JAVA实现导出Excel表
来源:互联网 发布:c语言源小程序代码大全 编辑:程序博客网 时间:2024/05/19 23:56
用java完成将数据导出到Excel中的功能,首先去了解一下有哪些Java ExcelAPI。
Java Aspose Cells
Java Aspose Cells 是一种纯粹的Java授权的Excel API,开发和供应商Aspose发布。这个API的最新版本是8.1.2,发布于2014年7月,是一个丰富而厚重的API(普通Java类和AWT类的组合)设计,可以读、写和操纵电子表格Excel的组件。此API常见用途如下:
- Excel报表,建立动态Excel报表
- 高保真的Excel渲染和打印
- 从Excel电子表格中导入和导出数据
- 生成,编辑,转换和电子表格
JXL
JXL是一款专为Selenium第三方框架,支持基于Web浏览器(数据是Web浏览器自动更新)数据驱动的自动化。然而,它也被用来作为JExcel API的一个共同的支持库,因为它的基本功能是可创建,读取和写入电子表格。基本特征如下:
- 生成Excel文件
- 从工作簿和电子表格导入数据
- 获得行和列的总数
- 注意:JXL只支持xls档案格式,并且不能处理大数据量。
JExcel
JExcel是由Team Dev开发提供纯行货API。利用这一点程序员可以很容易地读取,写入,显示和修改Excel工作簿中的两种格式:.xls和.XLSX。这个API可以很容易地嵌入Java的Swing和AWT。这个API的最新版本是Jexcel-2.6.12,发布于2009年,主要特点如下:
- 自动化Excel应用程序,工作簿,工作表等
- 在Java Swing应用程序作为普通的Swing组件嵌入到工作簿
- 事件侦听器添加到工作簿和电子表格
- 添加事件处理程序来处理的工作簿和电子表格事件的行为
- 添加本地对等开发定制功能
Apache POI
Apache POI是Apache软件基金会提供的100%开源库。大多数中小规模的应用程序开发主要依赖于Apache POI(HSSF+ XSSF)。它支持Excel 库的所有基本功能; 然而,呈现和文本提取是它的主要特点。
这次我用到的是最后一种Apache POI。首先是一个总的方法exportExcel_2007,传入4个主要参数,分别是: sheetName 工作表的名称;dataset 数据源;fieldMap 类的英文属性和Excel中的中文列名的对应关系;sheetSize 每个工作表中记录的最大个数。
代码如下:
/** * @param sheetName 工作表的名称 * @param dataset 数据源 * @param fieldMap 类的英文属性和Excel中的中文列名的对应关系 * @param sheetSize 每个工作表中记录的最大个数 * @return * @throws Exception */ public <T> Workbook exportExcel_2007(String sheetName, List<T> dataset, LinkedHashMap<String, String> fieldMap, int sheetSize, List<ModelAttr> modelAttrs) throws Exception { if(dataset==null || dataset.size()==0) { throw new RuntimeException("没有任何数据"); } SXSSFWorkbook wb = new SXSSFWorkbook(1000); //1.计算一共有多少个工作表 double sheetNum = Math.ceil(dataset.size()/new Integer(sheetSize).doubleValue()); //2.创建相应的工作表,并向其中填充数据 for(int i=0; i<sheetNum; i++){ //如果只有一个工作表的情况 if(1==sheetNum){ Sheet sheet = wb.createSheet(sheetName); fillSheet(sheet, dataset, fieldMap, 0, dataset.size()-1,modelAttrs); setColumnBorderAndColor(wb,sheet); //有多个工作表的情况 }else{ Sheet sheet = wb.createSheet(sheetName+(i+1)); //获取开始索引和结束索引 int firstIndex=i*sheetSize; int lastIndex=(i+1)*sheetSize-1>dataset.size()-1 ? dataset.size()-1 : (i+1)*sheetSize-1; //填充工作表 fillSheet(sheet, dataset, fieldMap, firstIndex, lastIndex,modelAttrs); setColumnBorderAndColor(wb,sheet); } } return wb; }
将工作表创建出来,就需要对表头和表体进行填充。因为我这里的表头是动态的,因此多传入了一个参数进行相关判断。填充表头和表体的函数是fillSheet。
代码如下:
/** * @MethodName : fillSheet * @Description : 向工作表中填充数据 * @param sheet 工作表 * @param list 数据源 * @param fieldMap 中英文字段对应关系的Map * @param firstIndex 开始索引 * @param lastIndex 结束索引 */ private <T> void fillSheet( Sheet sheet, List<T> list, LinkedHashMap<String,String> fieldMap, int firstIndex, int lastIndex, List<ModelAttr> modelAttrs )throws Exception{ //定义存放英文字段名和中文字段名的数组 String[] enFields=new String[fieldMap.size()]; String[] cnFields=new String[fieldMap.size()]; //填充数组 int count=0; for(Map.Entry<String,String> entry:fieldMap.entrySet()){ enFields[count]=entry.getKey(); cnFields[count]=entry.getValue(); count++; } //填充表头 Row firstRow = sheet.createRow(0); for(int i=0;i<cnFields.length;i++){ firstRow.createCell(i).setCellValue(cnFields[i]); } //填充内容 int rowNo=1; for(int index=firstIndex;index<=lastIndex;index++){ Row row = sheet.createRow(rowNo); //获取单个对象 Map<String,Object> item= (Map<String, Object>) list.get(index); for(int i=0;i<enFields.length;i++){ ModelAttrType type = null; for(ModelAttr modelAttr : modelAttrs){ if(enFields[i].equals(modelAttr.getAttrCode())){ type = modelAttr.getAttrType(); } } String value = getFieldValueByNameSequence(enFields[i], item,type); String fieldValue=value==null ? "" : value; row.createCell(i).setCellValue(fieldValue); } rowNo++; } //设置自动列宽 setColumnAutoSize(sheet, 512); }
首先将表头的数据放入两个数组中,一个是中文表头,一个是英文code,用来匹配表体。然后中文表体填充到新建的firstRow中。
在表头完成后,根据数据源填充表体,因为数据源是一个复杂的mapList,所以需要对填充的value进行提取处理。我这里写了几个方法,其中针对不同类型的数据处理写了一个感知器,感知器的不用类型处理的代码太多,就不贴了。总之能把你想要放的数据取出来就可以,不用写很复杂。
代码如下:
/** * @MethodName : getFieldValueByNameSequence * @Description : * 根据属性名获取属性值 * * @param fieldNameSequence 简单属性名 * @param o 对象 * @return 属性值 * @throws Exception */ private String getFieldValueByNameSequence(String fieldNameSequence, Map<String,Object> o,ModelAttrType type) throws Exception{ String value=null; return value = getFieldValueByName(fieldNameSequence,o,type); }/** * @MethodName : getFieldValueByName * @Description : 根据字段名获取字段值 * @param fieldName 字段名 * @param o 对象 * @return 字段值 */ private String getFieldValueByName(String fieldName, Map<String,Object> o,ModelAttrType type) throws Exception{ Object value=null; value=getFieldByName(fieldName, o); String valueStr = insAttrValueAwareProcessor.convertToExcel(type, value); return valueStr; } /** * @MethodName : getFieldByName * @Description : 根据字段名获取字段 * @param fieldName 字段名 * @param * @return 字段 */ private static Object getFieldByName(String fieldName, Map<String,Object> o){ if(o == null){ return null; } return o.get(fieldName); }
填充完数据后,就需要简单设置一下工作表的样式,具体看实际情况。
代码如下:
/** * @MethodName : setColumnAutoSize * @Description : 设置工作表自动列宽和首行加粗 * @param ws */ private static void setColumnAutoSize(Sheet ws,int extraWith){ //获取本列的最宽单元格的宽度 for(int i=0;i<ws.getRow(0).getPhysicalNumberOfCells();i++){ int colWith=0; for(int j=0;j<ws.getLastRowNum();j++){ String content=ws.getRow(j).getCell(i).getStringCellValue(); int cellWith=content.length(); if(colWith<cellWith){ colWith=cellWith; } } //设置单元格的宽度为最宽宽度+额外宽度 ws.setColumnWidth(i, colWith*extraWith); } } /** * 设置工作表单元格边框和首行背景色 * @param wb * @param ws */ private static void setColumnBorderAndColor(SXSSFWorkbook wb,Sheet ws){ XSSFCellStyle cellBorderStyle = (XSSFCellStyle)wb.createCellStyle(); XSSFCellStyle cellColorStyle = (XSSFCellStyle)wb.createCellStyle(); for(int i=0;i<ws.getPhysicalNumberOfRows();i++){ Row row = ws.getRow(i); for(int j=0;j<ws.getRow(0).getPhysicalNumberOfCells();j++){ Cell cell = row.getCell(j); Cell cellFirst = ws.getRow(0).getCell(j); //给单元格设置边框 cellBorderStyle.setBorderBottom(BorderStyle.THIN); cellBorderStyle.setBorderTop(BorderStyle.THIN); cellBorderStyle.setBorderLeft(BorderStyle.THIN); cellBorderStyle.setBorderRight(BorderStyle.THIN); //给第一行设置边框和背景 cellColorStyle.setFillForegroundColor(IndexedColors.AQUA.getIndex()); cellColorStyle.setFillPattern(FillPatternType.SOLID_FOREGROUND); cellColorStyle.setBorderBottom(BorderStyle.THIN); cellColorStyle.setBorderTop(BorderStyle.THIN); cellColorStyle.setBorderLeft(BorderStyle.THIN); cellColorStyle.setBorderRight(BorderStyle.THIN); cell.setCellStyle(cellBorderStyle); cellFirst.setCellStyle(cellColorStyle); } } }
有想深入了解学习Apache POI的,可以看看这篇教程Apache POI教程。我也对其进行了参考学习。
- 实现java导出Excel表
- Java 实现导出excel表
- Java 实现导出excel表
- Java 实现导出excel表
- JAVA实现导出Excel表
- java实现Excel导出
- java实现excel导出
- JAVA导出EXCEL实现
- java实现Excel导出
- java实现导出Excel
- Java 实现导出excel表 POI
- Java 实现导出excel表 POI
- Java 实现导出excel表 POI
- Java 实现导出excel表 POI
- Java 实现导出excel表 POI
- Java 实现导出excel表 POI
- Java 实现导出excel表 POI
- Java 实现导出excel表 POI
- react-native中的flex和flexGrow异同点
- Android类的XML属性,相关方法及说明
- DataTable 导出Excel
- Apache Storm学习笔记一:创建Storm集群
- DATE_SUB函数计算相对时间
- JAVA实现导出Excel表
- 用冒泡法给四个数据排序
- 牛客网---2016---搜狐扎金花
- 11.8第6节课
- java与php时间戳转换
- SPEC 虚拟机配置
- 笔记 jquery.trim()
- Java设计模式——观察者模式
- 最短路径(迪杰斯特拉)