|
|
|
|
@ -7,18 +7,21 @@ import org.apache.commons.lang3.CharUtils;
|
|
|
|
|
import org.apache.commons.lang3.StringUtils;
|
|
|
|
|
import org.apache.poi.hssf.usermodel.*;
|
|
|
|
|
import org.apache.poi.hssf.util.HSSFColor;
|
|
|
|
|
import org.apache.poi.ss.usermodel.*;
|
|
|
|
|
|
|
|
|
|
import javax.servlet.http.HttpServletResponse;
|
|
|
|
|
import java.io.IOException;
|
|
|
|
|
import java.io.OutputStream;
|
|
|
|
|
import java.lang.reflect.Field;
|
|
|
|
|
import java.util.ArrayList;
|
|
|
|
|
import java.util.Collection;
|
|
|
|
|
import java.util.List;
|
|
|
|
|
import java.util.concurrent.*;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
public class ExportExcelUtil {
|
|
|
|
|
|
|
|
|
|
private final int SPLIT_COUNT = 1000;
|
|
|
|
|
private final int SPLIT_COUNT = 10000;
|
|
|
|
|
|
|
|
|
|
private static List<String> fieldName = null;
|
|
|
|
|
|
|
|
|
|
@ -56,21 +59,75 @@ public class ExportExcelUtil {
|
|
|
|
|
return fieldData;
|
|
|
|
|
}
|
|
|
|
|
public void expordExcel(String tableThNames,String fieldCns,Collection list,String fileName,HttpServletResponse response) throws Exception {
|
|
|
|
|
this.createWorkbook(tableThNames,fieldCns,list,fileName,response);
|
|
|
|
|
}
|
|
|
|
|
public void createWorkbook(String tableThNames,String fieldCns,Collection list,String fileName,HttpServletResponse response) throws InterruptedException, IOException, ExecutionException {
|
|
|
|
|
this.fieldName = getFieldName(tableThNames);
|
|
|
|
|
this.fieldData = getFieldData(fieldCns,list);
|
|
|
|
|
this.fileName = fileName;
|
|
|
|
|
|
|
|
|
|
// 记录开始时间
|
|
|
|
|
long startTime = System.currentTimeMillis();
|
|
|
|
|
|
|
|
|
|
try {
|
|
|
|
|
OutputStream os = response.getOutputStream();
|
|
|
|
|
response.reset();
|
|
|
|
|
response.setContentType("application/OCTET-STREAM;charset=gbk");
|
|
|
|
|
response.setHeader("pragma", "no-cache");
|
|
|
|
|
fileName = new String(fileName.getBytes("utf-8"), "iso-8859-1");
|
|
|
|
|
response.setHeader("Content-disposition", "attachment;filename=\"" + fileName + "\"");
|
|
|
|
|
response.setBufferSize(1024);
|
|
|
|
|
workBook = createWorkbook();
|
|
|
|
|
workBook.write(os);
|
|
|
|
|
os.close();
|
|
|
|
|
response.setBufferSize(1024 * 10);
|
|
|
|
|
|
|
|
|
|
int rows = fieldData.size();
|
|
|
|
|
int sheetNum = (rows + SPLIT_COUNT - 1) / SPLIT_COUNT;
|
|
|
|
|
if (sheetNum == 0) {
|
|
|
|
|
sheetNum = 1;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
int cpuCores = Runtime.getRuntime().availableProcessors();
|
|
|
|
|
int threadPoolSize = 2 * cpuCores;
|
|
|
|
|
|
|
|
|
|
ExecutorService executor = Executors.newFixedThreadPool(threadPoolSize);
|
|
|
|
|
CompletionService<HSSFWorkbook> completionService = new ExecutorCompletionService<>(executor);
|
|
|
|
|
List<Future<HSSFWorkbook>> futures = new ArrayList<>();
|
|
|
|
|
|
|
|
|
|
for (int i = 1; i <= sheetNum; i++) {
|
|
|
|
|
final int index = i;
|
|
|
|
|
futures.add(completionService.submit(() -> createSheet(index, rows)));
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
HSSFWorkbook mainWorkbook = new HSSFWorkbook();
|
|
|
|
|
for (int i = 1; i <= sheetNum; i++) {
|
|
|
|
|
HSSFWorkbook workBook = completionService.take().get();
|
|
|
|
|
HSSFSheet sheet = workBook.getSheetAt(0);
|
|
|
|
|
HSSFSheet mainSheet = mainWorkbook.createSheet("Sheet " + i);
|
|
|
|
|
copySheet(sheet, mainSheet);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
try (OutputStream outputStream = os) {
|
|
|
|
|
mainWorkbook.write(outputStream);
|
|
|
|
|
}
|
|
|
|
|
public HSSFWorkbook createWorkbook() {
|
|
|
|
|
|
|
|
|
|
long endTime = System.currentTimeMillis();
|
|
|
|
|
long duration = (endTime - startTime) / 1000;
|
|
|
|
|
System.out.println("任务总耗时: " + duration + " 秒");
|
|
|
|
|
|
|
|
|
|
executor.shutdown();
|
|
|
|
|
} catch (Exception e) {
|
|
|
|
|
e.printStackTrace();
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/*this.fieldName = getFieldName(tableThNames);
|
|
|
|
|
this.fieldData = getFieldData(fieldCns,list);
|
|
|
|
|
this.fileName = fileName;
|
|
|
|
|
OutputStream os = response.getOutputStream();
|
|
|
|
|
response.reset();
|
|
|
|
|
response.setContentType("application/OCTET-STREAM;charset=gbk");
|
|
|
|
|
response.setHeader("pragma", "no-cache");
|
|
|
|
|
fileName = new String(fileName.getBytes("utf-8"), "iso-8859-1");
|
|
|
|
|
response.setHeader("Content-disposition", "attachment;filename=\"" + fileName + "\"");
|
|
|
|
|
response.setBufferSize(1024 * 10);
|
|
|
|
|
|
|
|
|
|
workBook = new HSSFWorkbook();
|
|
|
|
|
int rows = fieldData.size();
|
|
|
|
|
int sheetNum = 0;
|
|
|
|
|
@ -83,7 +140,111 @@ public class ExportExcelUtil {
|
|
|
|
|
if(sheetNum == 0){
|
|
|
|
|
sheetNum = 1;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
int cpuCores = Runtime.getRuntime().availableProcessors(); // 获取CPU核心数
|
|
|
|
|
int threadPoolSize = 2 * cpuCores; // 设置线程池大小为2倍CPU核心数
|
|
|
|
|
|
|
|
|
|
System.out.println("线程池大小为:"+ threadPoolSize);
|
|
|
|
|
|
|
|
|
|
ExecutorService executor = Executors.newFixedThreadPool(threadPoolSize); // 创建固定大小的线程池
|
|
|
|
|
Future<?>[] futures = new Future[sheetNum];
|
|
|
|
|
|
|
|
|
|
// 创建一个主工作簿
|
|
|
|
|
HSSFWorkbook mainWorkbook = new HSSFWorkbook();
|
|
|
|
|
|
|
|
|
|
// 记录开始时间
|
|
|
|
|
long startTime = System.currentTimeMillis();
|
|
|
|
|
|
|
|
|
|
for (int i = 1; i <= sheetNum; i++) {
|
|
|
|
|
final int index = i;
|
|
|
|
|
futures[i - 1] = executor.submit(() -> {
|
|
|
|
|
HSSFWorkbook workBook = new HSSFWorkbook();
|
|
|
|
|
// 创建工作表并设置样式
|
|
|
|
|
HSSFSheet sheet = workBook.createSheet("Sheet " + index);
|
|
|
|
|
HSSFRow headRow = sheet.createRow((short) 0);
|
|
|
|
|
HSSFCellStyle cellStyle = workBook.createCellStyle();
|
|
|
|
|
cellStyle.setAlignment(HSSFCellStyle.ALIGN_CENTER);
|
|
|
|
|
cellStyle.setVerticalAlignment(HSSFCellStyle.VERTICAL_CENTER);
|
|
|
|
|
|
|
|
|
|
HSSFFont font = workBook.createFont();
|
|
|
|
|
font.setBoldweight(HSSFFont.BOLDWEIGHT_BOLD);
|
|
|
|
|
font.setColor(HSSFColor.RED.index);
|
|
|
|
|
font.setFontHeightInPoints((short) 12);
|
|
|
|
|
cellStyle.setFont(font);
|
|
|
|
|
|
|
|
|
|
for (int j = 0; j < fieldName.size(); j++) {
|
|
|
|
|
HSSFCell cell = headRow.createCell( j);
|
|
|
|
|
sheet.setColumnWidth(j, 6000);
|
|
|
|
|
cell.setCellType(HSSFCell.CELL_TYPE_STRING);
|
|
|
|
|
if(fieldName.get(j) != null){
|
|
|
|
|
cell.setCellStyle(cellStyle);
|
|
|
|
|
cell.setCellValue((String) fieldName.get(j));
|
|
|
|
|
}else{
|
|
|
|
|
cell.setCellValue("-");
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
HSSFCellStyle cellStyle1 = workBook.createCellStyle();
|
|
|
|
|
cellStyle1.setAlignment(HSSFCellStyle.ALIGN_CENTER);
|
|
|
|
|
cellStyle1.setVerticalAlignment(HSSFCellStyle.VERTICAL_CENTER);
|
|
|
|
|
//数字格式
|
|
|
|
|
for (int k = 0; k < (rows < SPLIT_COUNT ? rows : SPLIT_COUNT); k++) {
|
|
|
|
|
if (((index - 1) * SPLIT_COUNT + k) >= rows)
|
|
|
|
|
break;
|
|
|
|
|
HSSFRow row = sheet.createRow((short) (k + 1));
|
|
|
|
|
ArrayList<String> rowList = (ArrayList<String>) fieldData.get((index - 1) * SPLIT_COUNT + k);
|
|
|
|
|
for (int n = 0; n < rowList.size(); n++) {
|
|
|
|
|
HSSFCell cell = row.createCell( n);
|
|
|
|
|
if(rowList.get(n) != null){
|
|
|
|
|
cell.setCellStyle(cellStyle1);
|
|
|
|
|
cell.setCellValue((String) rowList.get(n).toString());
|
|
|
|
|
}else{
|
|
|
|
|
cell.setCellValue("");
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
//设置自动列宽
|
|
|
|
|
for (int j = 0; j < rows; j++) {
|
|
|
|
|
sheet.autoSizeColumn(j);
|
|
|
|
|
int width = sheet.getColumnWidth(j)*2;
|
|
|
|
|
if(width < 3000){
|
|
|
|
|
sheet.setColumnWidth(j,sheet.getColumnWidth(j)*17/10);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
//冻结表头
|
|
|
|
|
sheet.createFreezePane( 0, 1, 0, 1 );
|
|
|
|
|
|
|
|
|
|
return workBook;
|
|
|
|
|
});
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// 等待所有任务完成
|
|
|
|
|
for (Future<?> future : futures) {
|
|
|
|
|
future.get();
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// 按照顺序添加sheet页到主工作簿
|
|
|
|
|
for (int i = 1; i <= sheetNum; i++) {
|
|
|
|
|
HSSFWorkbook workBook = (HSSFWorkbook) futures[i - 1].get(); // 获取已完成的工作簿
|
|
|
|
|
HSSFSheet sheet = workBook.getSheetAt(0); // 假设每个工作簿只有一个Sheet
|
|
|
|
|
HSSFSheet mainSheet = mainWorkbook.createSheet("Sheet " + i);
|
|
|
|
|
copySheet(sheet, mainSheet); // 复制Sheet到主工作簿
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// 写入输出流
|
|
|
|
|
try (OutputStream outputStream = os) {
|
|
|
|
|
mainWorkbook.write(outputStream);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// 记录结束时间
|
|
|
|
|
long endTime = System.currentTimeMillis();
|
|
|
|
|
|
|
|
|
|
// 计算并输出耗时(单位:秒)
|
|
|
|
|
long duration = (endTime - startTime) / 1000;
|
|
|
|
|
System.out.println("任务总耗时: " + duration + " 秒");
|
|
|
|
|
|
|
|
|
|
executor.shutdown(); // 关闭线程池*/
|
|
|
|
|
|
|
|
|
|
/*for (int i = 1; i <= sheetNum; i++) {
|
|
|
|
|
HSSFSheet sheet = workBook.createSheet("Sheet " + i);
|
|
|
|
|
HSSFRow headRow = sheet.createRow((short) 0);
|
|
|
|
|
HSSFCellStyle cellStyle = workBook.createCellStyle();
|
|
|
|
|
@ -137,9 +298,79 @@ public class ExportExcelUtil {
|
|
|
|
|
//冻结表头
|
|
|
|
|
sheet.createFreezePane( 0, 1, 0, 1 );
|
|
|
|
|
}
|
|
|
|
|
workBook.write(os);
|
|
|
|
|
os.close();*/
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
public HSSFWorkbook createSheet(int index, int totalRows) {
|
|
|
|
|
HSSFWorkbook workBook = new HSSFWorkbook();
|
|
|
|
|
HSSFSheet sheet = workBook.createSheet("Sheet " + index);
|
|
|
|
|
|
|
|
|
|
HSSFRow headRow = sheet.createRow(0);
|
|
|
|
|
HSSFCellStyle cellStyle = createCellStyle(workBook);
|
|
|
|
|
HSSFFont font = createFont(workBook);
|
|
|
|
|
cellStyle.setFont(font);
|
|
|
|
|
|
|
|
|
|
for (int j = 0; j < fieldName.size(); j++) {
|
|
|
|
|
HSSFCell cell = headRow.createCell(j);
|
|
|
|
|
sheet.setColumnWidth(j, 6000);
|
|
|
|
|
cell.setCellStyle(cellStyle);
|
|
|
|
|
cell.setCellValue(fieldName.get(j));
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
HSSFCellStyle cellStyle1 = createCellStyle(workBook);
|
|
|
|
|
int startRow = (index - 1) * SPLIT_COUNT;
|
|
|
|
|
int endRow = Math.min(startRow + SPLIT_COUNT, totalRows);
|
|
|
|
|
|
|
|
|
|
for (int k = startRow; k < endRow; k++) {
|
|
|
|
|
HSSFRow row = sheet.createRow(k - startRow + 1);
|
|
|
|
|
List<String> rowList = fieldData.get(k);
|
|
|
|
|
for (int n = 0; n < rowList.size(); n++) {
|
|
|
|
|
HSSFCell cell = row.createCell(n);
|
|
|
|
|
cell.setCellStyle(cellStyle1);
|
|
|
|
|
cell.setCellValue(rowList.get(n));
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
for (int j = 0; j < fieldName.size(); j++) {
|
|
|
|
|
sheet.autoSizeColumn(j);
|
|
|
|
|
int width = sheet.getColumnWidth(j) * 2;
|
|
|
|
|
if (width < 3000) {
|
|
|
|
|
sheet.setColumnWidth(j, sheet.getColumnWidth(j) * 17 / 10);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
sheet.createFreezePane(0, 1, 0, 1);
|
|
|
|
|
return workBook;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
public HSSFCellStyle createCellStyle(HSSFWorkbook workBook) {
|
|
|
|
|
HSSFCellStyle cellStyle = workBook.createCellStyle();
|
|
|
|
|
cellStyle.setAlignment(HSSFCellStyle.ALIGN_CENTER);
|
|
|
|
|
cellStyle.setVerticalAlignment(HSSFCellStyle.VERTICAL_CENTER);
|
|
|
|
|
return cellStyle;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
public HSSFFont createFont(HSSFWorkbook workBook) {
|
|
|
|
|
HSSFFont font = workBook.createFont();
|
|
|
|
|
font.setBoldweight(HSSFFont.BOLDWEIGHT_BOLD);
|
|
|
|
|
font.setColor(HSSFColor.RED.index);
|
|
|
|
|
font.setFontHeightInPoints((short) 12);
|
|
|
|
|
return font;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
public void copySheet(HSSFSheet sourceSheet, HSSFSheet targetSheet) {
|
|
|
|
|
for (int i = 0; i <= sourceSheet.getLastRowNum(); i++) {
|
|
|
|
|
HSSFRow sourceRow = sourceSheet.getRow(i);
|
|
|
|
|
if (sourceRow != null) {
|
|
|
|
|
HSSFRow targetRow = targetSheet.createRow(i);
|
|
|
|
|
for (int j = 0; j < sourceRow.getLastCellNum(); j++) {
|
|
|
|
|
targetRow.createCell(j).setCellValue(sourceRow.getCell(j).getStringCellValue());
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
public static String fieldToProperty(String field) {
|
|
|
|
|
if (null == field) {
|
|
|
|
|
return "";
|
|
|
|
|
|