用poi框架进行批量导入导出实例

来源:互联网 发布:知乎精华推荐 编辑:程序博客网 时间:2024/04/29 06:38
Apache POI是Apache软件基金会的开放源码函式库,POI提供API给Java程式对Microsoft Office格式档案读和写的功能。我们这里使用poi对数据库中的数据进行批量导出,以及从Excel文件中的数据批量导入到数据库中。

 

批量导出:

步骤:1.导入架包:

          poi-3.0-rc4-20070503.jar、poi-contrib-3.0-rc4-20070503.jar、poi-scratchpad-3.0-rc4-20070503.jar

          2.Excel操纵类,可以根据Excel模板来生成Excel对象(模板代码)

          3.生成Excel文件提供下载

实例代码:

Excel操纵类:

[html] view plaincopy
  1. package cn.test.excel;  
  2.   
  3. import java.util.Date;  
  4. import java.util.HashMap;  
  5. import java.util.Iterator;  
  6. import java.util.Map;  
  7. import java.util.Properties;  
  8. import java.util.Set;  
  9.   
  10. import org.apache.commons.logging.Log;  
  11. import org.apache.commons.logging.LogFactory;  
  12. import org.apache.poi.hssf.usermodel.HSSFCell;  
  13. import org.apache.poi.hssf.usermodel.HSSFCellStyle;  
  14. import org.apache.poi.hssf.usermodel.HSSFRow;  
  15. import org.apache.poi.hssf.usermodel.HSSFSheet;  
  16. import org.apache.poi.hssf.usermodel.HSSFWorkbook;  
  17. import org.apache.poi.poifs.filesystem.POIFSFileSystem;  
  18.   
  19. /**  
  20.  *   
  21.  * 功能描述: Excel操纵类,可以根据Excel模板来生成Excel对象<br>  
  22.  * 版本信息:1.0 <br>  
  23.  * Copyright: Copyright (c) 2005<br>  
  24.  */  
  25. public class ExcelTemplate {  
  26.     private static Log logger = LogFactory.getLog(ExcelTemplate.class);  
  27.     private static final String DATAS = "datas";  
  28.       
  29.     private HSSFWorkbook workbook;  
  30.     private HSSFSheet sheet;  
  31.     private HSSFRow currentRow;  
  32.     private Map styles = new HashMap(); //数据行的默认样式配置  
  33.     private Map confStyles = new HashMap(); //通过设置"#STYLE_XXX"来标识的样式配置  
  34.     private int initrow; //数据输出起始行  
  35.     private int initcol; //数据输出起始列  
  36.     private int num; //index number  
  37.     private int currentcol; //当前列  
  38.     private int currentRowIndex; //当前行index  
  39.     private int rowheight = 22; //行高  
  40.     private int lastLowNum = 0;  
  41.     private String cellStyle = null;  
  42.       
  43.     private ExcelTemplate() {  
  44.     }  
  45.       
  46.     /**  
  47.      * 使用默认模板创建ExcelTemplate对象  
  48.      * @return 根据模板已初始化完成的ExcelTemplate对象  
  49.      */  
  50.     public static ExcelTemplate newInstance(){  
  51.         return newInstance("templates/default.xls");  
  52.     }  
  53.   
  54.     /**  
  55.      * 指定模板创建ExcelTemplate对象  
  56.      * @param templates 模板名称  
  57.      * @return 根据模板已初始化完成的ExcelTemplate对象  
  58.      */  
  59.     public static ExcelTemplate newInstance(String templates){  
  60.         try {  
  61.             ExcelTemplate excel = new ExcelTemplate();  
  62.             POIFSFileSystem fs = new POIFSFileSystem(  
  63.                     Thread.currentThread().getContextClassLoader()  
  64.                     .getResourceAsStream(templates));  
  65.             excel.workbook = new HSSFWorkbook(fs);  
  66.             excel.sheet = excel.workbook.getSheetAt(0);  
  67.               
  68.             //查找配置  
  69.             excel.initConfig();  
  70.               
  71.             //查找其它样式配置  
  72.             excel.readCellStyles();  
  73.               
  74.             //删除配置行  
  75.             excel.sheet.removeRow( excel.sheet.getRow(excel.initrow) );  
  76.               
  77.             return excel;  
  78.         } catch (Exception e) {  
  79.             e.printStackTrace();  
  80.             logger.trace("创建Excel对象出现异常",e);  
  81.             throw new RuntimeException("创建Excel对象出现异常");  
  82.         }  
  83.     }  
  84.       
  85.       
  86.     /**  
  87.      * 设置特定的单元格样式,此样式可以通过在模板文件中定义"#STYLE_XX"来得到,如:  
  88.      * #STYLE_1,传入的参数就是"STYLE_1"  
  89.      * @param style   
  90.      */  
  91.     public void setCellStyle(String style){  
  92.         cellStyle = style;  
  93.     }  
  94.       
  95.     /**  
  96.      * 取消特定的单元格格式,恢复默认的配置值,即DATAS所在行的值  
  97.      */  
  98.     public void setCellDefaultStyle(){  
  99.         cellStyle = null;  
  100.     }  
  101.       
  102.     /**  
  103.      * 创建新行  
  104.      * @param index 从0开始计数  
  105.      */  
  106.     public void createRow(int index){  
  107.         //如果在当前插入数据的区域有后续行,则将其后面的行往后移动  
  108.         if(lastLowNum > initrow && index > 0){  
  109.             sheet.shiftRows(index + initrow ,lastLowNum + index,1,true,true);  
  110.         }  
  111.         currentRow = sheet.createRow(index + initrow);  
  112.         currentRow.setHeight((short)rowheight);  
  113.         currentRowIndex = index;  
  114.         currentcol = initcol;  
  115.     }  
  116.       
  117.     /**  
  118.      * 根据传入的字符串值,在当前行上创建新列  
  119.      * @param value 列的值(字符串)  
  120.      */  
  121.     public void createCell(String value){  
  122.         HSSFCell cell = createCell();  
  123.         cell.setCellType(HSSFCell.CELL_TYPE_STRING);  
  124.         cell.setCellValue(value);  
  125.     }  
  126.       
  127.     /**  
  128.      * 根据传入的日期值,在当前行上创建新列  
  129.      * 在这种情况下(传入日期),你可以在模板中定义对应列  
  130.      * 的日期格式,这样可以灵活通过模板来控制输出的日期格式  
  131.      * @param value 日期  
  132.      */  
  133.     public void createCell(Date value){  
  134.         HSSFCell cell = createCell();  
  135.         cell.setCellValue(value);  
  136.     }  
  137.       
  138.     /**  
  139.      * 创建当前行的序列号列,通常在一行的开头便会创建  
  140.      * 注意要使用这个方法,你必需在创建行之前调用initPageNumber方法  
  141.      */  
  142.     public void createSerialNumCell(){  
  143.         HSSFCell cell = createCell();  
  144.         cell.setCellValue(currentRowIndex + num);  
  145.     }  
  146.       
  147.     private HSSFCell createCell(){  
  148.         HSSFCell cell = currentRow.createCell((short)currentcol++);  
  149.         cell.setEncoding(HSSFCell.ENCODING_UTF_16);  
  150.         HSSFCellStyle style = (HSSFCellStyle)styles.get(new Integer(cell.getCellNum()));  
  151.         if(style != null){  
  152.             cell.setCellStyle(style);  
  153.         }  
  154.           
  155.         //设置了特定格式  
  156.         if(cellStyle != null){  
  157.             HSSFCellStyle ts = (HSSFCellStyle)confStyles.get(cellStyle);  
  158.             if(ts != null){  
  159.                 cell.setCellStyle(ts);  
  160.             }  
  161.         }  
  162.         return cell;  
  163.     }  
  164.       
  165.     /**  
  166.      * 获取当前HSSFWorkbook的实例  
  167.      * @return  
  168.      */  
  169.     public HSSFWorkbook getWorkbook(){  
  170.         return workbook;  
  171.     }  
  172.       
  173.     /**  
  174.      * 获取模板中定义的单元格样式,如果没有定义,则返回空  
  175.      * @param style 模板定义的样式名称  
  176.      * @return 模板定义的单元格的样式,如果没有定义则返回空  
  177.      */  
  178.     public HSSFCellStyle getTemplateStyle(String style){  
  179.         return (HSSFCellStyle)confStyles.get(style);  
  180.     }  
  181.       
  182.     /**  
  183.      * 替换模板中的文本参数  
  184.      * 参数以“#”开始  
  185.      * @param props  
  186.      */  
  187.     public void replaceParameters(Properties props){  
  188.         if(props == null || props.size() == 0){  
  189.             return;  
  190.         }  
  191.         Set propsets = props.entrySet();  
  192.         Iterator rowit = sheet.rowIterator();  
  193.         while(rowit.hasNext()){  
  194.             HSSFRow row = (HSSFRow)rowit.next();  
  195.             if(row == null) continue;  
  196.             int cellLength = row.getLastCellNum();  
  197.             for(int i=0; i<cellLength; i++){  
  198.                 HSSFCell cell = (HSSFCell)row.getCell((short)i);  
  199.                 if(cell == null) continue;  
  200.                 String value = cell.getStringCellValue();  
  201.                 if(value != null && value.indexOf("#") != -1){  
  202.                     for (Iterator iter = propsets.iterator(); iter.hasNext();) {  
  203.                         Map.Entry entry = (Map.Entry) iter.next();  
  204.                         value = value.replaceAll("#"+entry.getKey(),(String)entry.getValue());  
  205.                     }  
  206.                 }  
  207.                 cell.setEncoding(HSSFCell.ENCODING_UTF_16);  
  208.                 cell.setCellValue(value);  
  209.             }  
  210.         }  
  211.     }  
  212.       
  213.     /**  
  214.      * 初始化Excel配置  
  215.      */  
  216.     private void initConfig(){  
  217.         lastLowNum = sheet.getLastRowNum();  
  218.         Iterator rowit = sheet.rowIterator();  
  219.         boolean configFinish = false;  
  220.         while(rowit.hasNext()){  
  221.             if(configFinish){  
  222.                 break;  
  223.             }  
  224.             HSSFRow row = (HSSFRow)rowit.next();  
  225.             if(row == null) continue;  
  226.             int cellLength = row.getLastCellNum();  
  227.             int rownum = row.getRowNum();  
  228.             for(int i=0; i<cellLength; i++){  
  229.                 HSSFCell cell = (HSSFCell)row.getCell((short)i);  
  230.                 if(cell == null) continue;  
  231.                 String config = cell.getStringCellValue();  
  232.                 if(DATAS.equalsIgnoreCase(config)){  
  233.                     //本行是数据开始行和样式配置行,需要读取相应的配置信息  
  234.                     initrow = row.getRowNum();  
  235.                     rowheight = row.getHeight();  
  236.                     initcol = cell.getCellNum();  
  237.                     configFinish = true;  
  238.                 }  
  239.                 if(configFinish){  
  240.                     readCellStyle(cell);  
  241.                 }                 
  242.             }  
  243.         }  
  244.     }  
  245.       
  246.     /**  
  247.      * 读取cell的样式  
  248.      * @param cell  
  249.      */  
  250.     private void readCellStyle(HSSFCell cell){  
  251.         HSSFCellStyle style = cell.getCellStyle();  
  252.         if(style == null) return;  
  253.         styles.put(new Integer(cell.getCellNum()),style);  
  254.     }  
  255.       
  256.     /**  
  257.      * 读取模板中其它单元格的样式配置  
  258.      */  
  259.     private void readCellStyles(){  
  260.         Iterator rowit = sheet.rowIterator();  
  261.         while(rowit.hasNext()){  
  262.             HSSFRow row = (HSSFRow)rowit.next();  
  263.             if(row == null) continue;  
  264.             int cellLength = row.getLastCellNum();  
  265.             for(int i=0; i<cellLength; i++){  
  266.                 HSSFCell cell = (HSSFCell)row.getCell((short)i);  
  267.                 if(cell == null) continue;  
  268.                 String value = cell.getStringCellValue();  
  269.                 if(value != null && value.indexOf("#STYLE_") != -1){  
  270.                     HSSFCellStyle style = cell.getCellStyle();  
  271.                     if(style == null) continue;  
  272.                     confStyles.put(value.substring(1),style);  
  273.                       
  274.                     //remove it  
  275.                     row.removeCell(cell);  
  276.                 }  
  277.             }  
  278.         }  
  279.     }  
  280. }  


 

生成Excel文件并提供下载

[html] view plaincopy
  1. package cn.test.web.manager;  
  2.   
  3. import java.io.IOException;  
  4. import java.util.List;  
  5. import javax.servlet.ServletException;  
  6. import javax.servlet.http.HttpServlet;  
  7. import javax.servlet.http.HttpServletRequest;  
  8. import javax.servlet.http.HttpServletResponse;  
  9. import cn.itcast.dao.impl.BookDaoImpl;  
  10. import cn.itcast.domain.Book;  
  11. import cn.itcast.excel.ExcelTemplate;  
  12.   
  13. public class ExcelServlet extends HttpServlet {  
  14.   
  15.     public void doGet(HttpServletRequest request, HttpServletResponse response)  
  16.             throws ServletException, IOException {  
  17.             //导出Excel文件,不需要返回值,因为在方法的内部已经处理完成response  
  18.             //HttpServletRequest request =ServletActionContext.getRequest();  
  19.             String chcCreateDate=request.getParameter("svrDueId");  
  20.             BookDaoImpl bd =new BookDaoImpl();  
  21.             List customers = bd.getAll();//从数据库中获取要导出的集合  
  22.             //获取模板样式,需自行创建  
  23.             ExcelTemplate template = ExcelTemplate.newInstance("cn/test/excel/export_template.xls");    
  24.             for(int i=0; i<customers.size(); i++){  
  25.                 Book book = (Book)customers.get(i);  
  26.                 //创建一行  
  27.                 template.createRow(i);  
  28.                 //创建列  
  29.                 template.createCell(book.getId().toString());  
  30.                 template.createCell(book.getName().toString());  
  31.                 template.createCell(book.getAuthor());  
  32.                 template.createCell(book.getDescription());  
  33.             }  
  34.             //提供下载  
  35.             //HttpServletResponse response = ServletActionContext.getResponse();  
  36.             response.reset();  
  37.             response.setContentType("application/x-download;charset=GBK");  
  38.             response.setHeader("Content-Disposition", "attachment;filename=Book_"+System.currentTimeMillis()+".xls");  
  39.             try {  
  40.                 template.getWorkbook().write(response.getOutputStream());  
  41.             } catch (IOException e) {  
  42.                 e.printStackTrace();  
  43.             }  
  44.     }  
  45.     public void doPost(HttpServletRequest request, HttpServletResponse response)  
  46.             throws ServletException, IOException {  
  47.     }  
  48. }  


 

批量导入:

步骤:1.导入架包:

          poi-3.0-rc4-20070503.jar、poi-contrib-3.0-rc4-20070503.jar、poi-scratchpad-3.0-rc4-20070503.jar

          2.生成前台页面

          2.生出Excel工具类,将从Excel中获取的数据进行数据类型转换(模板代码)

          3.读取Excel文件批量上传

生出Excel工具类:

[html] view plaincopy
  1. package com.ssh.crm.excel;  
  2.   
  3. import org.apache.poi.hssf.usermodel.HSSFCell;  
  4. import org.apache.poi.hssf.usermodel.HSSFRow;  
  5.   
  6. public class ExcelUtils {  
  7.     public static int getIntCellValue(HSSFRow row,int index){  
  8.         int rtn = 0;  
  9.         try {  
  10.             HSSFCell cell = row.getCell((short)index);  
  11.             rtn = (int)cell.getNumericCellValue();  
  12.         } catch (RuntimeException e) {  
  13.         }  
  14.         return rtn;  
  15.     }  
  16.       
  17.     public static String getStringValue(HSSFRow row,int index){  
  18.         String rtn = "";  
  19.         try {  
  20.             HSSFCell cell = row.getCell((short)index);  
  21.             rtn = cell.getRichStringCellValue().getString();  
  22.         } catch (RuntimeException e) {  
  23.         }  
  24.         return rtn;  
  25.     }  
  26. }  

 

前台使用Struts标签库实现的

[html] view plaincopy
  1. <s:form action="UnderlyingData!importExcel.action" method="post" enctype="multipart/form-data">  
  2.     <s:file label="请选择文件" name="excel" required="true"/>  
  3.     <s:submit value="批量导入客户数据"></s:submit>  
  4. </s:form>  


读取Excel文件批量上传

[html] view plaincopy
  1. //导入Excel文件  
  2. protected File excel;  
  3. //封装要上传的文件  
  4. public File getExcel() {  
  5.     return excel;  
  6. }  
  7.   
  8. public void setExcel(File excel) {  
  9.     this.excel = excel;  
  10. }  
  11. public String importExcel(){  
  12.     List success = new ArrayList();  
  13.     ActionContext tx =ActionContext.getContext();  
  14.     String successanderror="";  
  15.     if(excel != null){  
  16.         try {  
  17.             //读取excel文件分析Excel文件中的数据  
  18.             HSSFWorkbook wb = new HSSFWorkbook(new FileInputStream(excel));  
  19.               
  20.             //读取第一页的内容  
  21.             HSSFSheet sheet = wb.getSheetAt(0);  
  22.               
  23.             //从数据行开始读取数据  
  24.             System.out.println(sheet.getLastRowNum());  
  25.             for(int i=2; i<=sheet.getLastRowNum(); i++){  
  26.                 HSSFRow row = sheet.getRow(i);  
  27.                 Product product =new Product();  
  28.                 //名称  
  29.                 product.setProdName(ExcelUtils.getStringValue(row, 1));  
  30.                 product.setProdType(ExcelUtils.getStringValue(row, 2));  
  31.                 product.setProdBatch(ExcelUtils.getStringValue(row, 3));  
  32.                 product.setProdUnit(ExcelUtils.getStringValue(row, 4));  
  33.                 product.setProdPrice(new Double(ExcelUtils.getIntCellValue(row, 5)));  
  34.                 //System.out.println(product.getProdPrice());  
  35.                 product.setProdMemo(ExcelUtils.getStringValue(row, 6));  
  36.                 //检查用户输入是否合法  
  37.                 if(product.getProdName().equals("")){  
  38.                     throw new Exception("名称项格式不正确,请检查第"+(i+1)+"行第"+2+"列!");  
  39.                 }else if(product.getProdType().equals("")){  
  40.                     throw new Exception("型号项格式不正确,请检查第"+(i+1)+"行第"+3+"列!");  
  41.                 }else if(product.getProdBatch().equals("")){  
  42.                     throw new Exception("等级/批次项格式不正确,请检查第"+(i+1)+"行第"+4+"列!");  
  43.                 }else if(product.getProdUnit().equals("")){  
  44.                     throw new Exception("单位项格式不正确,请检查第"+(i+1)+"行第"+5+"列!");  
  45.                 }else if(product.getProdPrice()==0.0){  
  46.                     throw new Exception("单价项格式不正确,请检查第"+(i+1)+"行第"+6+"列!");  
  47.                 }else if(product.getProdMemo().equals("")){  
  48.                     throw new Exception("备注项格式不正确,请检查第"+(i+1)+"行第"+7+"列!");  
  49.                 }  
  50.                   
  51.                 success.add(product);  
  52.             }  
  53.             successanderror=underlyingDataService.addproduct(success);  
  54.             tx.put("successList",success);  
  55.               
  56.         } catch (Exception e) {  
  57.             successanderror=e.getMessage();  
  58.         }finally{  
  59.             tx.put("sande",successanderror);  
  60.         }  
  61.     }  
  62.     return "inputdaoru";  
  63. }  
原创粉丝点击