웹사이트 검색

아파치 POI 튜토리얼


Apache POI 튜토리얼에 오신 것을 환영합니다. 때때로 우리는 Microsoft Excel 파일에서 데이터를 읽어야 하거나 주로 비즈니스 또는 재무 목적으로 Excel 형식으로 보고서를 생성해야 합니다. Java는 Excel 파일 작업에 대한 기본 제공 지원을 제공하지 않으므로 작업을 위한 오픈 소스 API를 찾아야 합니다. Excel용 Java API를 찾기 시작했을 때 대부분의 사람들이 JExcel 또는 Apache POI를 추천했습니다. 추가 조사 후 다음과 같은 주요 이유로 Apache POI를 사용하는 방법을 찾았습니다. 고급 기능과 관련된 몇 가지 다른 이유가 있지만 자세한 내용은 다루지 않겠습니다.

  • Apache 재단의 지원.
  • JExcel은 xlsx 형식을 지원하지 않지만 POI는 xls 및 xlsx 형식을 모두 지원합니다.
  • Apache POI는 대용량 파일에 적합하고 적은 메모리를 요구하는 스트림 기반 처리를 제공합니다.

아파치 POI

Apache POI는 Microsoft Excel 문서 작업을 위한 뛰어난 지원을 제공합니다. Apache POI는 스프레드시트의 XLS 및 XLSX 형식을 모두 처리할 수 있습니다. Apache POI API에 대한 몇 가지 중요한 사항은 다음과 같습니다.

  1. Apache POI에는 Excel 97(-2007) 파일 형식(예: XLS)에 대한 HSSF 구현이 포함되어 있습니다.
  2. Apache POI XSSF 구현은 Excel 2007 OOXML(.xlsx) 파일 형식에 사용해야 합니다.
  3. Apache POI HSSF 및 XSSF API는 Excel 스프레드시트를 읽고 쓰고 수정할 수 있는 메커니즘을 제공합니다.
  4. Apache POI는 또한 XSSF의 확장인 SXSSF API를 제공하여 매우 큰 Excel 시트와 함께 작동합니다. SXSSF API는 더 적은 메모리를 필요로 하며 매우 큰 스프레드시트로 작업할 때 적합하며 힙 메모리가 제한됩니다.
  5. 이벤트 모델과 사용자 모델의 두 가지 모델 중에서 선택할 수 있습니다. 이벤트 모델은 엑셀 파일을 토큰으로 읽고 이를 처리해야 하기 때문에 메모리가 덜 필요합니다. 사용자 모델은 보다 객체 지향적이고 사용하기 쉬우며 예제에서 이를 사용할 것입니다.
  6. Apache POI는 수식 작업, 색상 및 테두리 채우기를 통한 셀 스타일 생성, 글꼴, 머리글 및 바닥글, 데이터 유효성 검사, 이미지, 하이퍼링크 등과 같은 추가 Excel 기능에 대한 뛰어난 지원을 제공합니다.

Apache POI Maven 종속성

maven을 사용하는 경우 Apache POI 종속성을 아래에 추가하십시오.

<dependency>
	<groupId>org.apache.poi</groupId>
	<artifactId>poi</artifactId>
	<version>3.10-FINAL</version>
</dependency>
<dependency>
	<groupId>org.apache.poi</groupId>
	<artifactId>poi-ooxml</artifactId>
	<version>3.10-FINAL</version>
</dependency>

Apache POI 예제 - Excel 파일 읽기

package com.journaldev.excel.read;

public class Country {

	private String name;
	private String shortCode;
	
	public Country(String n, String c){
		this.name=n;
		this.shortCode=c;
	}
	
	public String getName() {
		return name;
	}
	public void setName(String name) {
		this.name = name;
	}
	public String getShortCode() {
		return shortCode;
	}
	public void setShortCode(String shortCode) {
		this.shortCode = shortCode;
	}
	
	@Override
	public String toString(){
		return name + "::" + shortCode;
	}
	
}

Excel 파일을 국가 목록으로 읽는 Apache POI 예제 프로그램은 다음과 같습니다. ReadExcelFileToList.java

package com.journaldev.excel.read;

import java.io.FileInputStream;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;

import org.apache.poi.hssf.usermodel.HSSFWorkbook;
import org.apache.poi.ss.usermodel.Cell;
import org.apache.poi.ss.usermodel.Row;
import org.apache.poi.ss.usermodel.Sheet;
import org.apache.poi.ss.usermodel.Workbook;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;

public class ReadExcelFileToList {

	public static List<Country> readExcelData(String fileName) {
		List<Country> countriesList = new ArrayList<Country>();
		
		try {
			//Create the input stream from the xlsx/xls file
			FileInputStream fis = new FileInputStream(fileName);
			
			//Create Workbook instance for xlsx/xls file input stream
			Workbook workbook = null;
			if(fileName.toLowerCase().endsWith("xlsx")){
				workbook = new XSSFWorkbook(fis);
			}else if(fileName.toLowerCase().endsWith("xls")){
				workbook = new HSSFWorkbook(fis);
			}
			
			//Get the number of sheets in the xlsx file
			int numberOfSheets = workbook.getNumberOfSheets();
			
			//loop through each of the sheets
			for(int i=0; i < numberOfSheets; i++){
				
				//Get the nth sheet from the workbook
				Sheet sheet = workbook.getSheetAt(i);
				
				//every sheet has rows, iterate over them
				Iterator<Row> rowIterator = sheet.iterator();
				while (rowIterator.hasNext()) 
		        {
					String name = "";
					String shortCode = "";
					
					//Get the row object
					Row row = rowIterator.next();
					
					//Every row has columns, get the column iterator and iterate over them
					Iterator<Cell> cellIterator = row.cellIterator();
		             
		            while (cellIterator.hasNext()) 
		            {
		            	//Get the Cell object
		            	Cell cell = cellIterator.next();
		            	
		            	//check the cell type and process accordingly
		            	switch(cell.getCellType()){
		            	case Cell.CELL_TYPE_STRING:
		            		if(shortCode.equalsIgnoreCase("")){
		            			shortCode = cell.getStringCellValue().trim();
		            		}else if(name.equalsIgnoreCase("")){
		            			//2nd column
		            			name = cell.getStringCellValue().trim();
		            		}else{
		            			//random data, leave it
		            			System.out.println("Random data::"+cell.getStringCellValue());
		            		}
		            		break;
		            	case Cell.CELL_TYPE_NUMERIC:
		            		System.out.println("Random data::"+cell.getNumericCellValue());
		            	}
		            } //end of cell iterator
		            Country c = new Country(name, shortCode);
		            countriesList.add(c);
		        } //end of rows iterator
				
				
			} //end of sheets for loop
			
			//close file input stream
			fis.close();
			
		} catch (IOException e) {
			e.printStackTrace();
		}
		
		return countriesList;
	}

	public static void main(String args[]){
		List<Country> list = readExcelData("Sample.xlsx");
		System.out.println("Country List\n"+list);
	}

}

이 프로그램은 이해하기 매우 쉽고 다음 단계를 포함합니다.

  1. 파일 유형에 따라 Workbook 인스턴스를 만듭니다. xlsx 형식의 경우 XSSFWorkbook이고 xls 형식의 경우 HSSFWorkbook입니다. 파일 이름을 기반으로 통합 문서 인스턴스를 가져오기 위해 팩터리 패턴이 있는 래퍼 클래스를 만들 수 있었습니다.
  2. 통합 문서 getNumberOfSheets()를 사용하여 시트 수를 가져온 다음 for 루프를 사용하여 각 시트를 구문 분석합니다. getSheetAt(int i) 메서드를 사용하여 Sheet 인스턴스를 가져옵니다.
  3. Row 반복자를 가져온 다음 Cell 반복자를 가져와 Cell 개체를 가져옵니다. 여기서 Apache POI는 반복자 패턴을 사용하고 있습니다.
  4. 스위치 케이스를 사용하여 셀 유형을 읽고 그에 따라 처리합니다.

이제 Apache POI 예제 프로그램을 실행하면 콘솔에 다음과 같은 출력이 생성됩니다.

Random data::1.0
Random data::2.0
Random data::3.0
Random data::4.0
Country List
[India::IND, Afghanistan::AFG, United States of America::USA, Anguilla::AIA, 
Denmark ::DNK, Dominican Republic ::DOM, Algeria ::DZA, Ecuador ::ECU]

Apache POI 예제 - Excel 파일 작성

apache POI에서 Excel 파일을 작성하는 것은 여기에서 먼저 통합 문서를 생성한다는 점을 제외하면 읽기와 유사합니다. 그런 다음 시트, 행 및 셀 값을 설정하고 FileOutputStream을 사용하여 파일에 씁니다. 위의 방법에서 국가 목록을 사용하여 단일 시트의 다른 파일에 저장하는 간단한 아파치 POI 예제를 작성해 보겠습니다. WriteListToExcelFile.java

package com.journaldev.excel.read;

import java.io.FileOutputStream;
import java.util.Iterator;
import java.util.List;

import org.apache.poi.hssf.usermodel.HSSFWorkbook;
import org.apache.poi.ss.usermodel.Cell;
import org.apache.poi.ss.usermodel.Row;
import org.apache.poi.ss.usermodel.Sheet;
import org.apache.poi.ss.usermodel.Workbook;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;

public class WriteListToExcelFile {

	public static void writeCountryListToFile(String fileName, List<Country> countryList) throws Exception{
		Workbook workbook = null;
		
		if(fileName.endsWith("xlsx")){
			workbook = new XSSFWorkbook();
		}else if(fileName.endsWith("xls")){
			workbook = new HSSFWorkbook();
		}else{
			throw new Exception("invalid file name, should be xls or xlsx");
		}
		
		Sheet sheet = workbook.createSheet("Countries");
		
		Iterator<Country> iterator = countryList.iterator();
		
		int rowIndex = 0;
		while(iterator.hasNext()){
			Country country = iterator.next();
			Row row = sheet.createRow(rowIndex++);
			Cell cell0 = row.createCell(0);
			cell0.setCellValue(country.getName());
			Cell cell1 = row.createCell(1);
			cell1.setCellValue(country.getShortCode());
		}
		
		//lets write the excel data to file now
		FileOutputStream fos = new FileOutputStream(fileName);
		workbook.write(fos);
		fos.close();
		System.out.println(fileName + " written successfully");
	}
	
	public static void main(String args[]) throws Exception{
		List<Country> list = ReadExcelFileToList.readExcelData("Sample.xlsx");
		WriteListToExcelFile.writeCountryListToFile("Countries.xls", list);
	}
}

Apache POI 예제 - Excel 수식 읽기

package com.journaldev.excel.read;

import java.io.FileInputStream;
import java.io.IOException;
import java.util.Iterator;

import org.apache.poi.ss.usermodel.Cell;
import org.apache.poi.ss.usermodel.Row;
import org.apache.poi.ss.usermodel.Sheet;
import org.apache.poi.ss.usermodel.Workbook;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;

public class ReadExcelFormula {

	public static void readExcelFormula(String fileName) throws IOException{
		
		FileInputStream fis = new FileInputStream(fileName);
		
		//assuming xlsx file
		Workbook workbook = new XSSFWorkbook(fis);
		Sheet sheet = workbook.getSheetAt(0);
		Iterator<Row> rowIterator = sheet.iterator();
		while (rowIterator.hasNext()) 
        {
			Row row = rowIterator.next();
			Iterator<Cell> cellIterator = row.cellIterator();
            
            while (cellIterator.hasNext()) 
            {
            	Cell cell = cellIterator.next();
            	switch(cell.getCellType()){
            	case Cell.CELL_TYPE_NUMERIC:
            		System.out.println(cell.getNumericCellValue());
            		break;
            	case Cell.CELL_TYPE_FORMULA:
            		System.out.println("Cell Formula="+cell.getCellFormula());
            		System.out.println("Cell Formula Result Type="+cell.getCachedFormulaResultType());
            		if(cell.getCachedFormulaResultType() == Cell.CELL_TYPE_NUMERIC){
            			System.out.println("Formula Value="+cell.getNumericCellValue());
            		}
            	}
            }
        }
	}
	
	public static void main(String args[]) throws IOException {
		readExcelFormula("FormulaMultiply.xlsx");
	}
}

위의 apache poi 예제 프로그램을 실행하면 다음과 같은 결과를 얻습니다.

1.0
2.0
3.0
4.0
Cell Formula=A1*A2*A3*A4
Cell Formula Result Type=0
Formula Value=24.0

Apache POI 예제 - Excel 쓰기 수식

경우에 따라 몇 가지 계산을 수행한 다음 셀 값을 작성해야 합니다. Excel 수식을 사용하여 이 계산을 수행할 수 있으며 계산에 사용된 셀 값이 변경되면 값이 변경되기 때문에 더 정확해집니다. apache poi api를 사용하여 수식으로 Excel 파일을 작성하는 간단한 예를 살펴보겠습니다. WriteExcelWithFormula.java

package com.journaldev.excel.read;

import java.io.FileOutputStream;
import java.io.IOException;

import org.apache.poi.ss.usermodel.Row;
import org.apache.poi.ss.usermodel.Sheet;
import org.apache.poi.ss.usermodel.Workbook;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;

public class WriteExcelWithFormula {

	public static void writeExcelWithFormula(String fileName) throws IOException{
		Workbook workbook = new XSSFWorkbook();
		Sheet sheet = workbook.createSheet("Numbers");
		Row row = sheet.createRow(0);
		row.createCell(0).setCellValue(10);
		row.createCell(1).setCellValue(20);
		row.createCell(2).setCellValue(30);
		//set formula cell
		row.createCell(3).setCellFormula("A1*B1*C1");
		
		//lets write to file
		FileOutputStream fos = new FileOutputStream(fileName);
		workbook.write(fos);
		fos.close();
		System.out.println(fileName + " written successfully");
	}
	
	public static void main(String[] args) throws IOException {
		writeExcelWithFormula("Formulas.xlsx");
	}
}