我们都知道java poi在导出数据到excel2003工作表中时一个工作表只能存储65536行数据,如果超过这个数据就会失败,excel2007并没有这个问题,但是为了兼容性我们通常都是导出到2003版本上的,下面我们看看如何用java poi解决这个问题,为了便于理解我就将整个excel poi导出功能贴出来了。
java poi自动sheet分页效果:
以下是service层的处理方法(关键)
/** * 如果达到50000条数据则重新创建工作表的逻辑 */ @Override public void exportExcel(List<HolidayItemForm> formList, ServletOutputStream outputStream){ try { //工作表名后面的数字,如表1,表2 int i = 0; //记录总行数 int rownum = 0; //记录每个sheet的行数 int tempnum = 0; //分页条数达到此条数则创建工作表 int page = 5; //创建工作薄 HSSFWorkbook workbook = new HSSFWorkbook(); //创建列标题栏样式 HSSFCellStyle cellStyle = ExcelUtils.createCellStyle(workbook, (short)10); while(true){ //创建工作表并应用上面的样式 HSSFSheet sheet = ExcelUtils.createWorkbook(workbook,cellStyle,++i); rownum++; //将数据库中的数据列表写入excel中 if(formList != null){ tempnum = 0; for (int j=rownum-i; j<formList.size(); j++) { //进入第2个sheet写出的行数从第2条数据开始(++tempnum等于1,因为标题行占了1行) HSSFRow row2 = sheet.createRow(++tempnum); rownum++; row2.createCell(0).setCellValue(formList.get(j).getUserId()); row2.createCell(1).setCellValue(formList.get(j).getUserName()); row2.createCell(2).setCellValue(formList.get(j).getDeptName()); row2.createCell(3).setCellValue(formList.get(j).getUserJob()); row2.createCell(4).setCellValue(formList.get(j).getTypeName()); row2.createCell(5).setCellValue(formList.get(j).getBeginDate()); row2.createCell(6).setCellValue(formList.get(j).getEndDate()); row2.createCell(7).setCellValue(formList.get(j).getHolidayHour()); row2.createCell(8).setCellValue(formList.get(j).getCreateDate()); //达到5条退出并创建另外一个sheet if(rownum%page == 0){ break; } } } //如果记录的行数等于集合的总行数则退出 if((rownum-i) == formList.size()){ break; } } //输出 workbook.write(outputStream); workbook.close(); } catch (IOException e) { e.printStackTrace(); } }
ExcelUtils工具类上的两个方法,跟解决此问题没什么关联,只是上面有用到,我就把它贴出来了。
/** * 创建列标题栏样式 * 水平垂直居中 */ public static HSSFCellStyle createCellStyle(HSSFWorkbook workbook, short fontSize) { HSSFCellStyle cellStyle = workbook.createCellStyle(); cellStyle.setAlignment(HorizontalAlignment.CENTER); cellStyle.setVerticalAlignment(VerticalAlignment.CENTER); HSSFFont font = workbook.createFont(); font.setBold(true); font.setFontHeightInPoints(fontSize); cellStyle.setFont(font); return cellStyle; } /** * 创建新工作表 */ public static HSSFSheet createWorkbook(HSSFWorkbook workbook,HSSFCellStyle cellStyle,int num) { HSSFSheet sheet = workbook.createSheet("明细"+num); sheet.setDefaultColumnWidth(18); String [] titles = {"工号","姓名","部门","职务","假期类型","开始日期","结束日期","请假小时","创建时间"}; HSSFRow row = sheet.createRow(0); for(int i=0; i<titles.length; i++){ HSSFCell cell = row.createCell(i); cell.setCellStyle(cellStyle); cell.setCellValue(titles[i]); } return sheet; }
Controller层传给service层一个list集合和outputstream输出流。
//导出假期明细列表 @RequiresPermissions("approval:holiday:detail:view") @RequestMapping("/holidaydetail/excelexport") public void exportExcel(HolidayItemForm form,HttpServletRequest request,HttpServletResponse response){ Map<String,Object> paramMap = new HashMap<>(); try { paramMap.put("companyId", form.getCompanyId()); paramMap.put("deployId", form.getDeployId()); paramMap.put("userId", form.getUserId()); //从数据库查找需要的信息集合 List<HolidayItemForm> formList = itemService.findPageByParam(paramMap); String currentTime = new SimpleDateFormat("yyyyMMddHHmmss").format(new Date()); response.setContentType("application/vnd.ms-excel"); //解决导出文件IE和其他浏览器中文名乱码问题 String filename = null; if(request.getHeader("User-Agent").indexOf("Mozilla") != -1){ filename = URLEncoder.encode("假期明细"+currentTime+".xls", "UTF-8"); }else{ filename = new String(("假期明细"+currentTime+".xls").getBytes(),"ISO8859-1"); } response.setHeader("Content-Disposition", "attachment;filename=" + filename); ServletOutputStream outputStream = response.getOutputStream(); //将上面查到的集合传给service层处理 itemService.exportExcel(formList,outputStream); if(outputStream != null){ outputStream.close(); } } catch (Exception e) { e.printStackTrace(); } }