Apache POI读写Excel文档入门(支持XLS和XLSX格式)

原文地址https://blog.csdn.net/u014527058/article/details/50818391

Java读写Office文档的库非常多,且都日趋成熟,比较常见的API有Apache POI、docx4j和UNO等。本文将以Apache POI为例,向大家介绍通过Java读写Excel文档的方法。


一、Apache POI简介


Apache POI 是用Java编写的免费开源的跨平台的 Java API,具有创建和维护各种符合Office OpenXML(OOXML)和OLE 2复合文档格式的功能,可对Word、Excel、PowerPoint进行读写操作。
目前该API的最新版本为3.14,于2016年3月2日发布。在本文中所使用的POI则为3.11版本。
值得一提的是,POI的全称是Poor Obfuscation Implementation,意为“简陋又模糊的实现”,这和slf4j(Simple Log Facade for Java,Java简单日志门面)的取名有异曲同工之妙。这两个东西实际上是非常强大的,但是它们的作者却说自己的东西很poor、很simple,不得不佩服外国人的谦虚。


二、JAR包依赖


Excel文档分为XLS(针对Excel 97-2003)格式和XLSX(针对Excel 2007及以后版本)格式,不同格式所需的JAR包依赖是不一样的。


下面的依赖仅支持XLS格式:

[html]  view plain  copy
  1. <dependency>  
  2.     <groupId>org.apache.poi</groupId>  
  3.     <artifactId>poi</artifactId>  
  4.     <version>3.11-beta1</version>  
  5. </dependency>  


以下依赖既支持XLS格式,也支持XLSX格式:


[html]  view plain  copy
  1. <dependency>  
  2.     <groupId>org.apache.poi</groupId>  
  3.     <artifactId>poi-ooxml</artifactId>  
  4.     <version>3.11-beta1</version>  
  5. </dependency>  


三、示例实体类


用户类。由用户名、密码、昵称组成。


[java]  view plain  copy
  1. package com.fhp.testpoi.entity;  
  2.   
  3. public class User {  
  4.     protected String username;  
  5.     protected String password;  
  6.     protected String nickname;  
  7.       
  8.     public User() {  
  9.         super();  
  10.     }  
  11.       
  12.     public User(String username, String password, String nickname) {  
  13.         this.username = username;  
  14.         this.password = password;  
  15.         this.nickname = nickname;  
  16.     }  
  17.       
  18.     public String getUsername() {  
  19.         return username;  
  20.     }  
  21.     public void setUsername(String username) {  
  22.         this.username = username;  
  23.     }  
  24.     public String getPassword() {  
  25.         return password;  
  26.     }  
  27.     public void setPassword(String password) {  
  28.         this.password = password;  
  29.     }  
  30.     public String getNickname() {  
  31.         return nickname;  
  32.     }  
  33.     public void setNickname(String nickname) {  
  34.         this.nickname = nickname;  
  35.     }  
  36.       
  37.     @Override  
  38.     public String toString() {  
  39.         StringBuffer sb = new StringBuffer();  
  40.           
  41.         sb.append("username=");  
  42.         sb.append(username);  
  43.         sb.append(";password=");  
  44.         sb.append(password);  
  45.         sb.append(";nickname=");  
  46.         sb.append(nickname);  
  47.           
  48.         return sb.toString();  
  49.     }  
  50. }  


四、读取Excel文档



总体思路如下:XLSX的文档读取类为XSSFWorkBook,其实现了WorkBook接口,可通过File类进行构造。然后通过Excel文档按照需求读取对应的工作表,再从工作表中根据所需行号等信息读取对应的行,最后根据列号定位到表中的单元格。该API可以从单元格中读取字符串、整形数、浮点数、日期和公式等数据。


读取XLSX格式文档:


[java]  view plain  copy
  1. package com.fhp.testpoi;  
  2.   
  3. import java.io.File;  
  4. import java.io.IOException;  
  5. import java.util.ArrayList;  
  6. import java.util.List;  
  7.   
  8. import org.apache.poi.openxml4j.exceptions.InvalidFormatException;  
  9. import org.apache.poi.ss.usermodel.Cell;  
  10. import org.apache.poi.ss.usermodel.Row;  
  11. import org.apache.poi.ss.usermodel.Sheet;  
  12. import org.apache.poi.ss.usermodel.Workbook;  
  13. import org.apache.poi.xssf.usermodel.XSSFWorkbook;  
  14.   
  15. import com.fhp.testpoi.entity.User;  
  16.   
  17. public class UserXlsxReader {  
  18.       
  19.     public List<User> read(File file) throws InvalidFormatException, IOException {  
  20.         Workbook workbook = new XSSFWorkbook(file);  
  21.         Sheet sheet = workbook.getSheetAt(0);  
  22.           
  23.         List<User> result = new ArrayList<User>();  
  24.           
  25.         int rowStart = sheet.getFirstRowNum() + 1;  
  26.         int rowEnd = sheet.getLastRowNum();  
  27.           
  28.         for(int i = rowStart; i <= rowEnd; i++) {  
  29.             Row row = sheet.getRow(i);        
  30.             User user = this.getUserFromRow(row);             
  31.             if(user != null) result.add(user);  
  32.         }  
  33.         workbook.close();  
  34.         return result;  
  35.     }  
  36.       
  37.     protected User getUserFromRow(Row row) {  
  38.         if(row == nullreturn null;  
  39.         int current = row.getFirstCellNum() + 1;  
  40.         Cell cell = row.getCell(current);  
  41.         if(null != cell) {  
  42.             User user = new User();  
  43.             user.setUsername(cell.getStringCellValue());  
  44.             current++;  
  45.               
  46.             cell = row.getCell(current);  
  47.             user.setPassword(cell.getStringCellValue());  
  48.             current++;  
  49.               
  50.             cell = row.getCell(current);  
  51.             user.setNickname(cell.getStringCellValue());  
  52.               
  53.             return user;  
  54.         }  
  55.         return null;  
  56.     }  
  57. }  

读取XLS格式文档,比读XLSX要稍微麻烦一些。

[java]  view plain  copy
  1. package com.fhp.testpoi;  
  2.   
  3. import java.io.File;  
  4. import java.io.FileInputStream;  
  5. import java.io.IOException;  
  6. import java.util.ArrayList;  
  7. import java.util.List;  
  8.   
  9. import org.apache.poi.hssf.usermodel.HSSFWorkbook;  
  10. import org.apache.poi.openxml4j.exceptions.InvalidFormatException;  
  11. import org.apache.poi.poifs.filesystem.POIFSFileSystem;  
  12. import org.apache.poi.ss.usermodel.Cell;  
  13. import org.apache.poi.ss.usermodel.Row;  
  14. import org.apache.poi.ss.usermodel.Sheet;  
  15. import org.apache.poi.ss.usermodel.Workbook;  
  16. import org.apache.poi.xssf.usermodel.XSSFWorkbook;  
  17.   
  18. import com.fhp.testpoi.entity.User;  
  19.   
  20. public class UserXlsxReader {  
  21.       
  22.     public List<User> read(File file) throws InvalidFormatException, IOException {  
  23.           
  24.         POIFSFileSystem poifsFileSystem = new POIFSFileSystem(new FileInputStream(file));  
  25.         Workbook workbook = new HSSFWorkbook(poifsFileSystem);  
  26.           
  27.         Sheet sheet = workbook.getSheetAt(0);  
  28.           
  29.         List<User> result = new ArrayList<User>();  
  30.           
  31.         int rowStart = sheet.getFirstRowNum() + 1;  
  32.         int rowEnd = sheet.getLastRowNum();  
  33.           
  34.         for(int i = rowStart; i <= rowEnd; i++) {  
  35.             Row row = sheet.getRow(i);        
  36.             User user = this.getUserFromRow(row);             
  37.             if(user != null) result.add(user);  
  38.         }  
  39.         workbook.close();  
  40.         return result;  
  41.     }  
  42.       
  43.     protected User getUserFromRow(Row row) {  
  44.         if(row == nullreturn null;  
  45.         int current = row.getFirstCellNum() + 1;  
  46.         Cell cell = row.getCell(current);  
  47.         if(null != cell) {  
  48.             User user = new User();  
  49.             user.setUsername(cell.getStringCellValue());  
  50.             current++;  
  51.               
  52.             cell = row.getCell(current);  
  53.             user.setPassword(cell.getStringCellValue());  
  54.             current++;  
  55.               
  56.             cell = row.getCell(current);  
  57.             user.setNickname(cell.getStringCellValue());  
  58.               
  59.             return user;  
  60.         }  
  61.         return null;  
  62.     }  
  63. }  

五、写入Excel文档


总体思路如下:和读取文档的思路相似,按照文件→工作表→行→列的方式进行定位。除了将Excel文档写入文件之外,还可以将Excel文档写入到流中,便于传输。
下面贴上写XLSX的代码。若需要写XLS格式的文档,把第33行的XSSFWorkBook改为HSSFWorkBook即可,这里就不贴了。


[java]  view plain  copy
  1. package com.fhp.testpoi;  
  2.   
  3. import java.io.File;  
  4. import java.io.FileOutputStream;  
  5. import java.io.IOException;  
  6. import java.io.OutputStream;  
  7. import java.util.Collection;  
  8.   
  9. import org.apache.poi.openxml4j.exceptions.InvalidFormatException;  
  10. import org.apache.poi.ss.usermodel.Cell;  
  11. import org.apache.poi.ss.usermodel.Row;  
  12. import org.apache.poi.ss.usermodel.Sheet;  
  13. import org.apache.poi.ss.usermodel.Workbook;  
  14. import org.apache.poi.xssf.usermodel.XSSFWorkbook;  
  15.   
  16. import com.fhp.testpoi.entity.User;  
  17.   
  18. public class UserXlsxWriter {  
  19.     protected File file;  
  20.     protected OutputStream os;  
  21.     protected Workbook book = null;  
  22.     public UserXlsxWriter() {  
  23.         super();  
  24.     }  
  25.       
  26.     public UserXlsxWriter(File file) throws IOException, InvalidFormatException {  
  27.         super();  
  28.         this.file = file;  
  29.         if(!file.exists()) {  
  30.             file.createNewFile();  
  31.         }  
  32.         os = new FileOutputStream(file);  
  33.         book = new XSSFWorkbook();  
  34.         Sheet sheet = book.createSheet("user");  
  35.           
  36.         String[] title = {"用户名""密码""昵称"};  
  37.         Row titleRow = sheet.createRow(0);  
  38.         for(int i = 0; i < title.length; i++) {  
  39.             Cell cell = titleRow.createCell(i + 1);  
  40.             cell.setCellValue(title[i]);  
  41.         }  
  42.     }  
  43.       
  44.     public void Write(User user) throws IOException {  
  45.         Sheet sheet = book.getSheet("user");  
  46.         int lastRowNum = sheet.getLastRowNum();  
  47.         Row currentRow = sheet.createRow(lastRowNum + 1);  
  48.         currentRow.createCell(0).setCellFormula("ROW() - 1");  
  49.         currentRow.createCell(1).setCellValue(user.getUsername());  
  50.         currentRow.createCell(2).setCellValue(user.getPassword());  
  51.         currentRow.createCell(3).setCellValue(user.getNickname());  
  52.     }  
  53.       
  54.     public void Write(Collection<User> users) throws IOException {  
  55.         for(User u : users) {  
  56.             this.Write(u);  
  57.         }  
  58.     }  
  59.       
  60.     public void Write(User... users) throws IOException {  
  61.         for(User u : users) {  
  62.             this.Write(u);  
  63.         }  
  64.     }  
  65.       
  66.     public void Extract() throws IOException {  
  67.         book.write(os);  
  68.         book.close();  
  69.     }  
  70. }  


六、测试类


读取Excel文档:

[java]  view plain  copy
  1. package com.fhp.testpoi;  
  2.   
  3. import static org.junit.Assert.*;  
  4.   
  5. import java.io.File;  
  6. import java.io.IOException;  
  7. import java.util.List;  
  8.   
  9. import org.apache.poi.openxml4j.exceptions.InvalidFormatException;  
  10. import org.junit.Test;  
  11.   
  12. import com.fhp.testpoi.entity.User;  
  13.   
  14. public class TestUserXlsxReader {  
  15.   
  16.     @Test  
  17.     public void testRead() throws InvalidFormatException, IOException {  
  18.         File file = new File("H:/testxlsx.xlsx");  
  19.         UserXlsxReader reader = new UserXlsxReader();  
  20.         List<User> users = reader.read(file);  
  21.         assertEquals(3, users.size());  
  22.     }  
  23. }  



写入Excel文档:


[java]  view plain  copy
  1. package com.fhp.testpoi;  
  2.   
  3. import static org.junit.Assert.*;  
  4.   
  5. import java.io.File;  
  6. import java.io.IOException;  
  7. import java.util.ArrayList;  
  8. import java.util.List;  
  9.   
  10. import org.apache.poi.openxml4j.exceptions.InvalidFormatException;  
  11. import org.junit.Test;  
  12.   
  13. import com.fhp.testpoi.entity.User;  
  14.   
  15. public class TestUserXlsxWriter {  
  16.   
  17.     @Test  
  18.     public void testWrite() throws InvalidFormatException, IOException {  
  19.         File file = new File("H:/testxlsx.xlsx");  
  20.         if(file.exists()) {  
  21.             file.delete();  
  22.         }  
  23.         UserXlsxWriter writer = new UserXlsxWriter(file);  
  24.           
  25.         User user1 = new User("admin""admin""Administrator");  
  26.         User user2 = new User("user1""user1""Sally");  
  27.         User user3 = new User("user2""zhangsan""张三");  
  28.           
  29.         writer.Write(user1);  
  30.         writer.Write(user2);  
  31.         writer.Write(user3);  
  32.         writer.Extract();  
  33.         assertTrue(file.exists());  
  34.     }  
  35.       
  36.     @Test  
  37.     public void testBatchWrite() throws InvalidFormatException, IOException {  
  38.         File file = new File("H:/testxlsxbatch.xlsx");  
  39.         if(file.exists()) {  
  40.             file.delete();  
  41.         }  
  42.         UserXlsxWriter writer = new UserXlsxWriter(file);  
  43.           
  44.         User user1 = new User("admin""admin""Administrator");  
  45.         User user2 = new User("user1""user1""Sally");  
  46.         User user3 = new User("user2""zhangsan""张三");  
  47.           
  48.         List<User> users = new ArrayList<User>();  
  49.           
  50.         users.add(user1);  
  51.         users.add(user2);  
  52.         users.add(user3);  
  53.           
  54.         writer.Write(users);  
  55.         writer.Extract();  
  56.         assertTrue(file.exists());  
  57.     }  
  58. }  

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值