最近写了一个Excel Util,参考API文档,自取 http://poi.apache.org/apidocs/
这次的excel功能主要是提供给后台导出。为了配合阿里云的oss上传,所以并没有生成到本地,而是直接生成一个流对象,之后就可以通过流的形式,直接上传到阿里云oss。此处没有阿里云的代码,阿里云的oss上传比较简单,就不上传了
请注意一下入参,原先是
第一版 public static <T> void listToExcel( List<T> objList List<String> objStrList, List<String> titleList, String sheetName, OutputStream outputStream ) {...}
这样写并不是有问题,而是遇到一个大的问题,就是入参的时候需要直接将所有对象都塞到objList这个对象里面,如果excel数据比较多,可能这个对象要堆积到上万,这时候对内存的压力是非常大的,要一直到整个excel导出完成后,这个对象才会被GC回收。如果此时有多个功能调用excel工具,容易造成内存溢出。
第二版 public static <T> void listToExcel( List<String> objStrList, List<String> titleList, String sheetName, OutputStream outputStream, Supplier<List<T>> supplier ) {...}
第二版就是最新的一个版本,通过一个Supplier,将每次入参的对象尽量变小,让调用方可以用过分次传入对象,每次生成完毕之后,可以直接GC,然后在进行下一次查询。
话不多说,直接贴代码。
public class ExcelUtil {
private static final Logger logger = LoggerFactory.getLogger(ExcelUtil.class);
private static final String SHEET_NAME = "new sheet";
/**
* @param supplier 数据源
* @param objStrList 映射关系属性值
* @param titleList 第一行属性名
* @MethodName : listToExcel
* @Description : 导出Excel(可以导出到本地文件系统,也可以导出到浏览器,工作表大小为2003支持的最大值)
*/
//cs:off
public static <T> void listToExcel(
List<String> objStrList,
List<String> titleList,
String sheetName,
OutputStream outputStream,
Supplier<List<T>> supplier
) {
sheetName = StringUtils.isNotBlank(sheetName) ? sheetName : SHEET_NAME;
XSSFWorkbook wb = new XSSFWorkbook();
//sheet样式定义【getColumnTopStyle()/getStyle()均为自定义方法 - 在下面 - 可扩展】
//获取列头样式对象
XSSFCellStyle columnTopStyle = getColumnTopStyle(wb);
//单元格样式对象
XSSFCellStyle style = getStyle(wb);
XSSFSheet sheet = wb.createSheet(sheetName);
XSSFRow row = sheet.createRow(0);
if (/*null == objList || */null == titleList || null == objStrList) {
logger.error("数据源为空,或者数据为空");
}
//写入第一行
for (int i = 0; i < titleList.size(); i++) {
XSSFCell cell = row.createCell(i);
cell.setCellType(HSSFCell.CELL_TYPE_STRING);
cell.setCellValue(titleList.get(i));
cell.setCellStyle(columnTopStyle);
}
//遍历对象值
try {
List<T> datas;
int rowNum = 1;
while (CollectionUtils.isNotEmpty(datas = supplier.get())) {
System.err.println(datas.get(0));
for (int i = 0; i < datas.size(); i++) {
XSSFRow row1 = sheet.createRow(rowNum);
T t = datas.get(i);
Class<?> aClass = t.getClass();
//Field[] declaredFields = aClass.getDeclaredFields();
for (int j = 0; j < objStrList.size(); j++) {
Field f = aClass.getDeclaredField(objStrList.get(j));
f.setAccessible(true);
Object o = f.get(t);
//值写入excel
XSSFCell cell = row1.createCell(j);
cell.setCellType(HSSFCell.CELL_TYPE_STRING);
cell.setCellValue(null == o ? "" : String.valueOf(o));
cell.setCellStyle(style);
}
rowNum = rowNum + 1;
}
}
try {
wb.write(outputStream);
} catch (IOException e) {
throw new RuntimeException(e);
}
} catch (
IllegalAccessException e) {
throw new RuntimeException(e);
} catch (
Exception e) {
logger.error("", e);
throw new RuntimeException(e);
} finally {
}
}
//cs:on
/*
* 列头单元格样式
*/
private static XSSFCellStyle getColumnTopStyle(XSSFWorkbook workbook) {
// 设置字体
XSSFFont font = workbook.createFont();
//设置字体大小
font.setFontHeightInPoints((short) 11);
//字体加粗
font.setBoldweight(HSSFFont.BOLDWEIGHT_BOLD);
//设置字体名字
font.setFontName("Courier New");
//设置样式;
XSSFCellStyle style = workbook.createCellStyle();
//设置底边框;
style.setBorderBottom(HSSFCellStyle.BORDER_THIN);
//设置底边框颜色;
style.setBottomBorderColor(HSSFColor.BLACK.index);
//设置左边框;
style.setBorderLeft(HSSFCellStyle.BORDER_THIN);
//设置左边框颜色;
style.setLeftBorderColor(HSSFColor.BLACK.index);
//设置右边框;
style.setBorderRight(HSSFCellStyle.BORDER_THIN);
//设置右边框颜色;
style.setRightBorderColor(HSSFColor.BLACK.index);
//设置顶边框;
style.setBorderTop(HSSFCellStyle.BORDER_THIN);
//设置顶边框颜色;
style.setTopBorderColor(HSSFColor.BLACK.index);
//在样式用应用设置的字体;
style.setFont(font);
//设置自动换行;
style.setWrapText(false);
//设置水平对齐的样式为居中对齐;
style.setAlignment(HSSFCellStyle.ALIGN_CENTER);
//设置垂直对齐的样式为居中对齐;
style.setVerticalAlignment(HSSFCellStyle.VERTICAL_CENTER);
return style;
}
/*
* 列数据信息单元格样式
*/
private static XSSFCellStyle getStyle(XSSFWorkbook workbook) {
// 设置字体
XSSFFont font = workbook.createFont();
//设置字体大小
//font.setFontHeightInPoints((short)10);
//字体加粗
//font.setBoldweight(HSSFFont.BOLDWEIGHT_BOLD);
//设置字体名字
font.setFontName("Courier New");
//设置样式;
XSSFCellStyle style = workbook.createCellStyle();
//设置底边框;
style.setBorderBottom(HSSFCellStyle.BORDER_THIN);
//设置底边框颜色;
style.setBottomBorderColor(HSSFColor.BLACK.index);
//设置左边框;
style.setBorderLeft(HSSFCellStyle.BORDER_THIN);
//设置左边框颜色;
style.setLeftBorderColor(HSSFColor.BLACK.index);
//设置右边框;
style.setBorderRight(HSSFCellStyle.BORDER_THIN);
//设置右边框颜色;
style.setRightBorderColor(HSSFColor.BLACK.index);
//设置顶边框;
style.setBorderTop(HSSFCellStyle.BORDER_THIN);
//设置顶边框颜色;
style.setTopBorderColor(HSSFColor.BLACK.index);
//在样式用应用设置的字体;
style.setFont(font);
//设置自动换行;
style.setWrapText(false);
//设置水平对齐的样式为居中对齐;
style.setAlignment(HSSFCellStyle.ALIGN_CENTER);
//设置垂直对齐的样式为居中对齐;
style.setVerticalAlignment(HSSFCellStyle.VERTICAL_CENTER);
return style;
}
}