java后端导出excel
最近工作中需要导出excel。这次机智一点做个笔记,顺便写了一个比较通用的工具类。自然目前不能生成java实体类属性嵌套多次的这种没办法导出了,后续有需要的时候我再改改。
首先,java后端导出excel需要的HSSFWorkbook或者XSSFWorkbook,实际上他们并没有什么区别,只是导出的格式不同而已(在我看来)。前者导出.xls格式,后者导出.xlsx格式的。不过新版的好像就没有这个区别了吧,因为我也是使用HSSFWorkbook,但是同样也能导出.xlsx格式的文件呦。
HSSFWorkbook(XSSFWorkbook)他们都是Apache的产品,你可以按照需求随意切换!他们没有实质上的太多的差别,听别人说他们还有一个差别就是HSSFWorkbook只能导出65535条数据,再大的话就会报错,而XSSFWorkbook可以导出数据量是非常大的(在下并没有测试,感兴趣的兄弟可以试一下),实际上一般我们也用不了导出超过65535条数据吧。
先看一下api吧!http://poi.apache.org/apidocs/dev/org/apache/poi/hssf/usermodel/HSSFWorkbook.html
接下来我就直接粘代码了
package com.ml.code.one.until; import org.apache.poi.hssf.usermodel.*;
import org.apache.poi.ss.usermodel.HorizontalAlignment;
import org.apache.poi.ss.usermodel.VerticalAlignment;
import org.apache.poi.ss.util.CellRangeAddress; import java.io.File;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.util.*;
import java.util.regex.Pattern;
import java.util.stream.Collectors; /**
* @author lhf
* @param <T>
* @since 1.0
* <p>
* 导出excel工具类,比较通用的呦
* </p>
*/
public class ExcelUtil<T> { /**
* 导出excel
* @param datas 要导出的数据
* @param excelName excel名字
* @param sheetHead 表头 key对应java中的属性名,每个key前边
* 加01-99,为了排序。value对应表头的中文名
* @param path 路径
* @param entity 分装属性名(如果有连表查询的话)
* @return -1其他异常 1导出成功 2目标文件被占用(文件已存在但是被其他应用占用) 0 导出失败(io)
* @throws IllegalAccessException
* @throws InvocationTargetException
*/
public int outExcel(Collection<T>datas, String excelName,
Map<String, String> sheetHead,String path,String... entity) throws IllegalAccessException, InvocationTargetException {
HSSFWorkbook workbook = new HSSFWorkbook(); //excel对象
HSSFSheet sheet = workbook.createSheet(excelName);
sheet.autoSizeColumn(1,true); //第一行表名
HSSFRow row = sheet.createRow(0);
HSSFCell cell = row.createCell(0);
cell.setCellValue(excelName); //获取表头集合中所有的key(那么顺序可能会乱)
Set<String> sheetKeySet = sheetHead.keySet();
//转换为list集合,并排序
List<String> sheetKey = sheetKeySet.stream().sorted().collect(Collectors.toList());//将set集合进行排序并转换成List集合
//合并单元格
sheet.addMergedRegion(new CellRangeAddress(0, 0, 0, sheetKey.size() - 1)); //设置单元格文字垂直居中,水平居中
HSSFCellStyle cellStyle = workbook.createCellStyle();
cellStyle.setVerticalAlignment(VerticalAlignment.CENTER);
cellStyle.setAlignment(HorizontalAlignment.CENTER_SELECTION);
cell.setCellStyle(cellStyle); //日期格式
HSSFCellStyle style = workbook.createCellStyle();
// HSSFDataFormat dataFormat = workbook.getCreationHelper().createDataFormat();
HSSFDataFormat dataFormat = workbook.createDataFormat();
style.setDataFormat(dataFormat.getFormat("yyyy/m/d")); //表头
HSSFRow row1 = sheet.createRow(1);
for (int i = 0; i < sheetKey.size(); i++) {
HSSFCell cell1 = row1.createCell(i);
cell1.setCellValue(sheetHead.get(sheetKey.get(i)));
cell1.setCellStyle(cellStyle);
} List<T> data = datas.stream().collect(Collectors.toList()); //将Collection转为List集合
T t=null; //获取到的泛型
//开始向excel表中添加信息
for (int i = 0; i < data.size(); i++) {//生成行
HSSFRow row2 = sheet.createRow(i + 2);
t=data.get(i);
Method[] declaredMethods = t.getClass().getDeclaredMethods();
for (int m = 0; m < sheetKey.size(); m++) {//拿到key值 key的数量代表列的数量
String key = sheetKey.get(m).substring(2);
String newKey = "get" + key.substring(0, 1).toUpperCase() + key.substring(1);//key首字母大写 for (int k = 0; k < declaredMethods.length; k++) {//遍历字段进行比较并添加信息//添加列信息
String methodName = declaredMethods[k].getName();//方法名
Object invoke1=null;
if (methodName.equals(newKey)) {//执行方法获取属性值
invoke1= declaredMethods[k].invoke(t);
}else if (entity.length>0){//如果有分装属性 A类中封装了B类 一下代码块就是执行B类中get方法
for (int j=0;j<entity.length;j++){
String s = "get"+entity[j].substring(0,1).toUpperCase()+entity[j].substring(1);
if (s.equals(methodName)){
Object oo = declaredMethods[k].invoke(t);
Method[] mes = oo.getClass().getDeclaredMethods();
for (int p=0;p<mes.length;p++){
if (mes[p].getName().equals(newKey)){
invoke1 = mes[p].invoke(oo);
}
} }
}
} if (invoke1 instanceof String){
boolean matches = Pattern.matches("[0-9]*", invoke1.toString());
if (matches){
Double invoke = (Double)invoke1;
row2.createCell(m).setCellValue(invoke);
}else {
String invoke= (String) invoke1;
row2.createCell(m).setCellValue(invoke);
}
} else if (invoke1 instanceof Integer){
Integer invoke = (Integer) invoke1;
row2.createCell(m).setCellValue(invoke);
} else if (invoke1 instanceof Short){
Short invoke = (Short) invoke1;
row2.createCell(m).setCellValue(invoke);
} else if (invoke1 instanceof Long){
Long invoke = (Long)invoke1;
row2.createCell(m).setCellValue(invoke);
} else if (invoke1 instanceof Boolean){
Boolean invoke = (Boolean)invoke1;
row2.createCell(m).setCellValue(invoke);
} else if (invoke1 instanceof Double){
Double invoke = (Double)invoke1;
row2.createCell(m).setCellValue(invoke);
} else if (invoke1 instanceof Float){
Float invoke = (Float)invoke1;
row2.createCell(m).setCellValue(invoke);
} else if (invoke1 instanceof Byte){
Byte invoke = (Byte)invoke1;
row2.createCell(m).setCellValue(invoke);
} else if (invoke1 instanceof Character){
Character invoke = (Character)invoke1;
row2.createCell(m).setCellValue(invoke);
} else if (invoke1 instanceof Date){
Date invoke = (Date)invoke1;
HSSFCell cell1 = row2.createCell(m);
cell1.setCellStyle(style);
cell1.setCellValue(invoke);
} else if (invoke1 instanceof java.sql.Date){
java.sql.Date invoke = (java.sql.Date)invoke1;
HSSFCell cell1 = row2.createCell(m);
cell1.setCellStyle(style);
cell1.setCellValue(invoke);
} //if 类型转换
}//for k
}//for m
}//for i //写入到文件
try {
File file = new File(path + excelName + ".xlsx");
if (!file.exists()) {
file.createNewFile();
}
workbook.write(file);
return 1;//导出成功
} catch (FileNotFoundException e){
e.printStackTrace();
return 2;//目标文件被占用
} catch (IOException e) {
e.printStackTrace();
return 0;//导出失败
} catch (Exception e){
e.printStackTrace();
return -1;//其他异常
}finally {
try {
if (workbook!=null)
workbook.close();
} catch (IOException e) {
e.printStackTrace();
}
}
} }
代码很简单,相信大家看的懂。有什么不明白的加我qq1490030544。
以下的伪代码是表名什么情况下不能用该类:

以上这种情况通过A类导出Excel时可以拿到B类的id,但是拿不到C类的id(虽然可以拿到C类的对象),这个后续可能我会改造一下,看时间安排吧
java后端导出excel的更多相关文章
- java后端导出excel表格
转载 :https://www.cnblogs.com/zhaoyuwei/p/9038135.html 不需要在实体类些@Excel(name = "登录名", width = ...
- 重构:以Java POI 导出EXCEL为例
重构 开头先抛出几个问题吧,这几个问题也是<重构:改善既有代码的设计>这本书第2章的问题. 什么是重构? 为什么要重构? 什么时候要重构? 接下来就从这几个问题出发,通过这几个问题来系统的 ...
- java 实现导出Excel文件
java 实现导出Excel(java生成 excel 并导出文件) 经常有有一些数据需要导出成 excel 格式 ,所以就需要实现啦 开始: 1.加入jar poi-3.6-20091214. ...
- java:POI导出excel
POI是一个开源项目,专用于java平台上操作MS OFFICE,企业应用开发中可用它方便导出Excel. 下面是使用示例: 1.maven中先添加依赖项 <dependency> < ...
- Java POI 导出EXCEL经典实现 Java导出Excel
转自http://blog.csdn.net/evangel_z/article/details/7332535 在web开发中,有一个经典的功能,就是数据的导入导出.特别是数据的导出,在生产管理或者 ...
- java导入导出excel常用操作小结及简单示例
POI中常用设置EXCEL的操作小结: 操作excel如下 HSSFWorkbook wb = new HSSFWorkbook(); //创建一个webbook,对应一个Excel文件 HSSFS ...
- java web 导出Excel 的工具类公用实现
平时我们在开发后端管理的系统时,经常会出现导出Excel的功能.这个功能很简单,但是呢,我一般就会使用公用的工具类,在一个Util中,暴露公用导出的接口,只需要传入需要导出的数据(一般使用list集合 ...
- [ExtJS5学习笔记]第三十四节 sencha extjs 5 grid表格之java后台导出excel
继上次使用js前端导出excel之后,还有一个主要大家比较关注的是后台实现导出excel,因为本人开发使用的java所以这里使用apache的开源项目poi进行后台excel的导出. 本文目录 本文目 ...
- 重构:以Java POI 导出EXCEL为例2
前言 上一篇博文已经将一些对象抽象成成员变量以及将一些代码块提炼成函数.这一节将会继续重构原有的代码,将一些函数抽象成类,增加成员变量,将传入的参数合成类等等. 上一篇博文地址:http://www. ...
随机推荐
- java常用第三方类库
Guava:来自Google的常用类库 Apache Commons:来自Apache的常用类库 Mockito:主要用于单元测试的mock DBUnit:测试中管理数据库测试数据 Rest Assu ...
- Causal Corpus 事件因果关系语料统计
Causal Corpus 事件因果关系语料统计 本文是对因果关系抽取领域数据库标注及开源情况的统计.除了对因果关系的标注,一些类似的语料也包含在内,从而为语料的使用提供灵活性,可以根据不同的目标选取 ...
- LocalStorage基础知识小结
cookie中每条cookie的存储空间为4k,localStorage中一般浏览器支持的是5M大小,这个在不同的浏览器中localStorage会有所不同. localStorage的写入,loca ...
- 在阿里做了5年技术Leader,我总结出这些套路!
转自 51CTO技术栈 内容 团队建设 团队管理 团队文化 沟通与辅导 招聘与解雇 互联网公司的技术团队管理通常分为两个方向:技术管理和团队管理,互联网公司的技术 TL 与传统软件公司的 PM 还是有 ...
- 17.3.12--time模块
import time #导入time模块 应用的时候有两种方式来表示时间: 1)时间戳 2)格式化的时间str(字符串) 3)元祖(struct_time)以及calendar 2---tim ...
- 吴裕雄--天生自然 PYTHON3开发学习:运算符
#!/usr/bin/python3 a = 21 b = 10 c = 0 c = a + b print ("1 - c 的值为:", c) c = a - b print ( ...
- Codeforces 1288C - Two Arrays
题目大意: 给定n和m,有两个数组,两个数组的长度都等于m 数组内每个元素都在1到n中 对于两个数组对应的位置i,必须满足a[i]<=b[i] a数组必须是不下降的序列 b数组必须是不上升的序列 ...
- python-day1 爬虫基础之HTTP基本原理
经过前几天的开发环境配置,今天终于正式开启学Python之路了,今天主要看了HTTP的基本原理,下边做一个总结: 1.首先要了解的就是URI和URL,URI的全拼是Uniform Resource I ...
- ant design for vue 解决 vue.esm.js?c5de:628 [Vue warn]: Invalid prop: custom validator check failed for prop "defaultValue". 的错误
错误重现: 在使用ant design for vue 的选择器插件的时候, 设置默认为为id(为数字) 报错: 解决办法: id为数字, 而defaultValue 的key 值必须为字符串, 将i ...
- Matlab高级教程_第二篇:Matlab相见恨晚的模块_02_并行运算-1
1 更高级的算法牵扯到更多重的循环和复杂的计算,尤其是现在人工智能的算法尤其如此.有些历史知识的人能够了解到,人工智能的很多基本算法其实近百年之前就有了,但是当时的计算机技术达不到去实现这些算法的要求 ...