1. package com.sgcc.lms.easypoi.util;
    2. import org.apache.poi.ss.usermodel.*;
    3. import org.apache.poi.ss.util.CellRangeAddress;
    4. import org.apache.poi.xssf.streaming.SXSSFWorkbook;
    5. import java.io.FileOutputStream;
    6. import java.util.*;
    7. /**
    8. * @Author: 李孟帅
    9. * @CreateTime: 2021/5/11$ 10:35$
    10. * @Description: TODO
    11. */
    12. public class Poi {
    13. private static CellStyle createTitleCellStyle(Workbook workbook) {
    14. CellStyle cellStyle = workbook.createCellStyle();
    15. cellStyle.setAlignment(HorizontalAlignment.CENTER);
    16. cellStyle.setVerticalAlignment(VerticalAlignment.CENTER);
    17. cellStyle.setBorderBottom(BorderStyle.THIN);
    18. cellStyle.setBottomBorderColor(IndexedColors.BLACK.index);
    19. cellStyle.setBorderLeft(BorderStyle.THIN);
    20. cellStyle.setLeftBorderColor(IndexedColors.BLACK.index);
    21. cellStyle.setBorderRight(BorderStyle.THIN);
    22. cellStyle.setRightBorderColor(IndexedColors.BLACK.index);
    23. cellStyle.setBorderTop(BorderStyle.THIN);
    24. cellStyle.setTopBorderColor(IndexedColors.BLACK.index);
    25. cellStyle.setFillForegroundColor(IndexedColors.GREY_40_PERCENT.index);
    26. cellStyle.setFillPattern(FillPatternType.SOLID_FOREGROUND);
    27. return cellStyle;
    28. }
    29. /**
    30. * 使用 SXSSFWorkbook 对象实现excel导出
    31. * (一般是导出百万级数据的excel)
    32. */
    33. public void exportBigDataExcel() {
    34. long startTime = System.currentTimeMillis(); //开始时间
    35. System.out.println("start execute time: " + new Date(startTime));
    36. // 1.创建工作簿
    37. // 阈值,内存中的对象数量最大值,超过这个值会生成一个临时文件存放到硬盘中
    38. SXSSFWorkbook wb = new SXSSFWorkbook(1000);
    39. //2.在Workbook中添加一个sheet,对应Excel文件中的sheet
    40. Sheet sheet = wb.createSheet();
    41. //3.设置样式以及字体样式
    42. CellStyle titleCellStyle = createTitleCellStyle(wb);
    43. CellStyle headCellStyle = createHeadCellStyle(wb);
    44. CellStyle cellStyle = createCellStyle(wb);
    45. //4.创建标题、表头,内容和合并单元格等操作
    46. int rowNum = 0;// 行号
    47. // 创建第一行,索引从0开始
    48. Row row0 = sheet.createRow(rowNum++);
    49. row0.setHeight((short) 800);// 设置行高
    50. String title = "这里是标题标题标题";
    51. Cell c00 = row0.createCell(0);
    52. c00.setCellValue(title);
    53. c00.setCellStyle(titleCellStyle);
    54. // 合并单元格,参数依次为起始行,结束行,起始列,结束列 (索引0开始)
    55. sheet.addMergedRegion(new CellRangeAddress(0, 0, 0, 6));//标题合并单元格操作,6为总列数
    56. // 第二行
    57. Row row1 = sheet.createRow(rowNum++);
    58. row1.setHeight((short) 500);
    59. String[] row_first = {"填表单位:", "", "", "", "", " xxxx年第x季度 ", ""};
    60. for (int i = 0; i < row_first.length; i++) {
    61. Cell tempCell = row1.createCell(i);
    62. tempCell.setCellStyle(headCellStyle);
    63. if (i == 0) {
    64. tempCell.setCellValue(row_first[i] + "测试单位");
    65. } else if (i == 5) {
    66. tempCell.setCellStyle(headCellStyle);
    67. tempCell.setCellValue(row_first[i]);
    68. } else {
    69. tempCell.setCellValue(row_first[i]);
    70. }
    71. }
    72. // 合并
    73. sheet.addMergedRegion(new CellRangeAddress(1, 1, 0, 4));
    74. sheet.addMergedRegion(new CellRangeAddress(1, 1, 5, 6));
    75. //第三行
    76. Row row2 = sheet.createRow(rowNum++);
    77. row2.setHeight((short) 700);
    78. String[] row_second = {"名称", "采集情况", "", "", "登记情况", "", "备注"};
    79. for (int i = 0; i < row_second.length; i++) {
    80. Cell tempCell = row2.createCell(i);
    81. tempCell.setCellValue(row_second[i]);
    82. tempCell.setCellStyle(headCellStyle);
    83. }
    84. // 合并
    85. sheet.addMergedRegion(new CellRangeAddress(2, 3, 0, 0));//名称
    86. sheet.addMergedRegion(new CellRangeAddress(2, 2, 1, 3));//人数情况
    87. sheet.addMergedRegion(new CellRangeAddress(2, 2, 4, 5));//登记情况
    88. sheet.addMergedRegion(new CellRangeAddress(2, 3, 6, 6));//备注
    89. //第三行
    90. Row row3 = sheet.createRow(rowNum++);
    91. row3.setHeight((short) 700);
    92. String[] row_third = {"", "登记数(人)", "办证总数(人)", "办证率(%)", "登记户数(户)", "登记时间", ""};
    93. for (int i = 0; i < row_third.length; i++) {
    94. Cell tempCell = row3.createCell(i);
    95. tempCell.setCellValue(row_third[i]);
    96. tempCell.setCellStyle(headCellStyle);
    97. }
    98. // 数据处理(创建100万条测试数据)
    99. List<Map<String, Object>> dataList = new ArrayList<Map<String, Object>>();
    100. for (int i = 0; i < 999999; i++) {
    101. Map<String, Object> map = new HashMap<String, Object>();
    102. map.put("name", "测试名称" + i);
    103. map.put("r1", "111");
    104. map.put("r2", "222");
    105. map.put("r3", "333");
    106. map.put("r4", "444");
    107. map.put("addTime", new Date());
    108. map.put("r6", "这里是备注" + i);
    109. dataList.add(map);
    110. }
    111. for (Map<String, Object> excelData : dataList) {
    112. Row tempRow = sheet.createRow(rowNum++);
    113. tempRow.setHeight((short) 500);
    114. // 循环单元格填入数据
    115. for (int j = 0; j < 7; j++) {
    116. Cell tempCell = tempRow.createCell(j);
    117. tempCell.setCellStyle(cellStyle);
    118. String tempValue;
    119. if (j == 0) {
    120. // 乡镇、街道名称
    121. tempValue = excelData.get("name").toString();
    122. } else if (j == 1) {
    123. // 登记数(人)
    124. tempValue = excelData.get("r1").toString();
    125. } else if (j == 2) {
    126. // 办证总数(人)
    127. tempValue = excelData.get("r2").toString();
    128. } else if (j == 3) {
    129. // 办证率(%)
    130. tempValue = excelData.get("r3").toString();
    131. } else if (j == 4) {
    132. // 登记户数(户)
    133. tempValue = excelData.get("r4").toString();
    134. } else if (j == 5) {
    135. // 登记日期
    136. tempValue = excelData.get("addTime").toString();
    137. } else {
    138. // 备注
    139. tempValue = excelData.get("r6").toString();
    140. }
    141. tempCell.setCellValue(tempValue);
    142. // sheet.autoSizeColumn(j);// 根据内容自动调整列宽,
    143. }
    144. }
    145. //设置列宽,必须在单元格设值以后进行
    146. sheet.setColumnWidth(0, 4000);//名称
    147. sheet.setColumnWidth(1, 3000);//登记数(人)
    148. sheet.setColumnWidth(2, 3000);//办证总数(人)
    149. sheet.setColumnWidth(3, 3000);//办证率(%)
    150. sheet.setColumnWidth(4, 3000);//登记户数(户)
    151. sheet.setColumnWidth(5, 6000);//登记时间
    152. sheet.setColumnWidth(6, 4000);//备注
    153. // 注释行
    154. Row remark = sheet.createRow(rowNum++);
    155. remark.setHeight((short) 500);
    156. String[] row_remark = {"注:表中的“办证率=办证总数÷登记数×100%”", "", "", "", "", "", ""};
    157. for (int i = 0; i < row_remark.length; i++) {
    158. Cell tempCell = remark.createCell(i);
    159. if (i == 0) {
    160. tempCell.setCellStyle(headCellStyle);
    161. } else {
    162. tempCell.setCellStyle(cellStyle);
    163. }
    164. tempCell.setCellValue(row_remark[i]);
    165. }
    166. int remarkRowNum = dataList.size() + 4;
    167. sheet.addMergedRegion(new CellRangeAddress(remarkRowNum, remarkRowNum, 0, 6));//注释行合并单元格
    168. // 尾行
    169. Row foot = sheet.createRow(rowNum++);
    170. foot.setHeight((short) 500);
    171. String[] row_foot = {"审核人:", "", "填表人:", "", "填表时间:", "", ""};
    172. for (int i = 0; i < row_foot.length; i++) {
    173. Cell tempCell = foot.createCell(i);
    174. tempCell.setCellStyle(cellStyle);
    175. if (i == 0) {
    176. tempCell.setCellValue(row_foot[i] + "张三");
    177. } else if (i == 2) {
    178. tempCell.setCellValue(row_foot[i] + "李四");
    179. } else if (i == 4) {
    180. tempCell.setCellValue(row_foot[i] + "xxxx");
    181. } else {
    182. tempCell.setCellValue(row_foot[i]);
    183. }
    184. }
    185. int footRowNum = dataList.size() + 5;
    186. // 注
    187. sheet.addMergedRegion(new CellRangeAddress(footRowNum, footRowNum, 0, 1));
    188. sheet.addMergedRegion(new CellRangeAddress(footRowNum, footRowNum, 2, 3));
    189. sheet.addMergedRegion(new CellRangeAddress(footRowNum, footRowNum, 4, 6));
    190. long finishedTime = System.currentTimeMillis(); //处理完成时间
    191. System.out.println("finished execute time: " + (finishedTime - startTime) / 1000 + "s");
    192. //导出
    193. String fileName = "C:\\Users\\lms\\Desktop\\报表文件名称.xlsx";
    194. try {
    195. FileOutputStream stream = new FileOutputStream(fileName);
    196. wb.write(stream);// 将数据写出去
    197. wb.close();
    198. stream.close();
    199. long stopTime = System.currentTimeMillis(); //写文件时间
    200. System.out.println("write xlsx file time: " + (stopTime - startTime) / 1000 + "s");
    201. } catch (Exception e) {
    202. e.printStackTrace();
    203. }
    204. }
    205. private static CellStyle createHeadCellStyle(Workbook workbook) {
    206. CellStyle cellStyle = workbook.createCellStyle();
    207. cellStyle.setAlignment(HorizontalAlignment.CENTER);
    208. cellStyle.setVerticalAlignment(VerticalAlignment.CENTER);
    209. cellStyle.setBorderBottom(BorderStyle.THIN);
    210. cellStyle.setBottomBorderColor(IndexedColors.BLACK.index);
    211. cellStyle.setBorderLeft(BorderStyle.THIN);
    212. cellStyle.setLeftBorderColor(IndexedColors.BLACK.index);
    213. cellStyle.setBorderRight(BorderStyle.THIN);
    214. cellStyle.setRightBorderColor(IndexedColors.BLACK.index);
    215. cellStyle.setBorderTop(BorderStyle.THIN);
    216. cellStyle.setTopBorderColor(IndexedColors.BLACK.index);
    217. cellStyle.setFillForegroundColor(IndexedColors.GREY_25_PERCENT.index);
    218. cellStyle.setFillPattern(FillPatternType.SOLID_FOREGROUND);
    219. return cellStyle;
    220. }
    221. private static CellStyle createCellStyle(Workbook workbook) {
    222. CellStyle cellStyle = workbook.createCellStyle();
    223. cellStyle.setAlignment(HorizontalAlignment.CENTER);
    224. cellStyle.setVerticalAlignment(VerticalAlignment.CENTER);
    225. cellStyle.setBorderBottom(BorderStyle.THIN);
    226. cellStyle.setBottomBorderColor(IndexedColors.BLACK.index);
    227. cellStyle.setBorderLeft(BorderStyle.THIN);
    228. cellStyle.setLeftBorderColor(IndexedColors.BLACK.index);
    229. cellStyle.setBorderRight(BorderStyle.THIN);
    230. cellStyle.setRightBorderColor(IndexedColors.BLACK.index);
    231. cellStyle.setBorderTop(BorderStyle.THIN);
    232. cellStyle.setTopBorderColor(IndexedColors.BLACK.index);
    233. return cellStyle;
    234. }
    235. public static void main(String[] args) {
    236. Poi poi = new Poi();
    237. poi.exportBigDataExcel();
    238. }
    239. }