Java利用POI操作Excel
POI提供了HSSF、XSSF以及SXSSF三种方式操作Excel。
其中:
HSSF:Excel97-2003版本,扩展名为.xls。一个sheet最大行数65536,最大列数256。
XSSF:Excel2007版本开始,扩展名为.xlsx。一个sheet最大行数1048576,最大列数16384。
SXSSF:是在XSSF基础上,POI3.8版本开始提供的支持低内存占用的操作方式,扩展名为.xlsx。
SXSSF支持低内存占用的方式是,通过一个滑动窗口来限制访问Row的数量从而达到低内存占用的目录,XSSF可以访问所有行。旧的行数据不再出现在滑动窗口中并变得无法访问,与此同时写到磁盘上。
在自动刷新的模式下,可以指定窗口中访问Row的数量,从而在内存中保持一定数量的Row。当达到这一数量时,在窗口中产生新的Row数据,并将低索引的数据从窗口中移动到磁盘中。
或者,滑动窗口的行数可以设定成自动增长的。它可以根据需要周期的根据一次明确的flushRow(int keepRows)调用来进行修改。
它的构造方法:
SXSSFWorkbook w3= new SXSSFWorkbook(100);
这个100,可以理解为POI操作时,内存中最多只有100行数据,当超过这个数据时,就将内存之前的数据删除,并且会在硬盘中生成临时文件。从而保证了低内存消耗。当然,你也可以将这个数字调大一点。
使用这三种方式并不太大差别,使用时只需要改变一下名称就可以。基本的流程都是首先创建对应的Workbook
对象,然后通过该对象得到Sheet表单,接下来针对表单进行相应的操作即可。
需要导入的依赖
可能出现的问题
Pom.xml中导入POI的依赖时,如果导入的是4.1.0的版本,直接使用XSSF和SXSSF好像是会报错的,需要将版本调整到3.1.0即可,我在使用的时候是这样做的:
<dependency>
<groupId>org.apache.poi</groupId>
<artifactId>poi</artifactId>
<version>3.14</version>
</dependency>
<dependency>
<groupId>org.apache.poi</groupId>
<artifactId>poi-ooxml</artifactId>
<version>3.14</version>
</dependency>
利用HSSFWorkbook写Excel
流程:
- 创建HSSFWorkbook对象
- 创建对应的工作表sheet (相当于Excel左下角的每一个工作表)
- 根据sheet来创建HSSFRow对象,拿到操作每一行的对象
- 通过每一行的对象来创建该行中每一个单元格HSSFCell对象,来往单元格中写入数据
- 最后定义要写入文件的输出流,利用
workbook.write(stream)
将数据写入文件中
下面给出示例代码:
public class POIWriteExcel {
/**
* POI HSSFWorkbook写入Excel文件
*/
public static void main(String[] args) throws Exception {
//创建Excel文件薄
HSSFWorkbook workbook=new HSSFWorkbook();
//创建工作表sheeet
HSSFSheet sheet=workbook.createSheet();
//创建第一行
HSSFRow row=sheet.createRow(0);
String[] title={"id","name","sex"};
HSSFCell cell=null;
for (int i=0;i<title.length;i++){
cell=row.createCell(i);
cell.setCellValue(title[i]);
}
//追加数据
for (int i=1;i<10;i++){
HSSFRow nextrow=sheet.createRow(i);
HSSFCell cell2=nextrow.createCell(0);
cell2.setCellValue("a"+i);
cell2=nextrow.createCell(1);
cell2.setCellValue("user"+i);
cell2=nextrow.createCell(2);
cell2.setCellValue("男");
}
//创建一个文件
File file=new File("userinfo.xls");
file.createNewFile();
FileOutputStream stream=FileUtils.openOutputStream(file);
workbook.write(stream);
stream.close();
}
}
打开后可以看到生成的结果如下:
利用HSSFWorkbook读Excel
流程:
- 创建xls文件的读入数据流FileInputStream
- 利用该文件数据流创建HSSFWorkbook对象
- 同样的根据该对象获取到某一工作表Sheet的对象(因为一个Excel中可能有多个工作表)
- 根据sheet来获得HSSFRow对象,拿到操作每一行的对象
- 通过每一行的对象来获得该行中每一个单元格HSSFCell对象,来读取单元格中的数据
- 最后定义要写入文件的输出流,利用
workbook.write(stream)
将数据写入文件中
代码示例:
public class POIReadExcel {
public static void main(String[] args) {
File file = new File("userinfo.xls");
try {
// 1. 创建文件输入流
BufferedInputStream bis = new BufferedInputStream(new FileInputStream(file));
// 2. 根据该数据流 创建HSSFWorkbook对象
HSSFWorkbook hssfWorkbook = new HSSFWorkbook(bis);
// 3. 获得到Sheet(这里只有一个工作表)
HSSFSheet sheet = hssfWorkbook.getSheetAt(0);
// 4. 判断sheet中有多少行数据
int rowNum = sheet.getLastRowNum();
// 5. 遍历每一行数据,获取HSSFRow对象
for(int i = 0; i < rowNum; i++)
{
HSSFRow row = sheet.getRow(i);
// 获取每一行的列数
short lastCellNum = row.getLastCellNum();
StringBuilder sb = new StringBuilder();
// 6. 遍历每一行中的每一列,获取到每个单元格中的值
for(int j = 0; j < lastCellNum; j++)
{
HSSFCell cell = row.getCell(j);
String stringCellValue = cell.getStringCellValue();
sb.append(stringCellValue);
sb.append(" ");
}
System.out.println(sb.toString());
}
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
}
控制台输出打印信息:
id name sex
a1 user1 男
a2 user2 男
a3 user3 男
a4 user4 男
a5 user5 男
a6 user6 男
a7 user7 男
a8 user8 男
小结
HSSF、XSSF、SXSSF是POI提供的功能递进的操作Excel的工具。XSSF相比于HSSF可以处理.xlsx后缀的Excel文本,但仍然有列数限制。而SXSSF则突破了列数的限制,可以写入更多行的数据。更多具体的原理,感兴趣的话可以深入继续研究。
小结
HSSF、XSSF、SXSSF是POI提供的功能递进的操作Excel的工具。XSSF相比于HSSF可以处理.xlsx后缀的Excel文本,但仍然有列数限制。而SXSSF则突破了列数的限制,可以写入更多行的数据。更多具体的原理,感兴趣的话可以深入继续研究。