Apache POI XSSF导出JTable数据至Excel时行空白问题求助
解决Apache POI拆分Excel工作表时出现空白行的问题
你猜的没错!问题确实出在XSSFRow row = sheet_Mark.createRow(i);这一行——你直接使用了原JTable的行索引i来创建目标工作表的行,这就会把原表中前面不属于当前用户的记录位置留成空白行。比如你的例子里,Mark的第一条记录在原表是第4条(循环索引i=3),你直接在sheet_Mark里创建第3行,那前3行自然是空的。
核心解决方案:为每个工作表单独维护行计数器
我们需要给每个目标工作表单独设置一个行计数器,而不是复用原表的索引。计数器初始为0,每往工作表里添加一条记录,计数器就自增1,这样就能保证每行都是连续创建的,不会跳过行产生空白。
修改后的代码示例
// 创建工作表 XSSFSheet sheet_Mark = workbook.createSheet("Mark"); XSSFSheet sheet_John = workbook.createSheet("John"); // 为每个工作表初始化行计数器 int markRowCounter = 0; int johnRowCounter = 0; for(int i = 0; i < jTable1.getRowCount(); i++){ Integer id_Values = (int) jTable1.getValueAt(i,0); String name_Values = (String) jTable1.getValueAt(i, 1); Integer age_Values = (int) jTable1.getValueAt(i,2); if(name_Values.equals("Mark")){ // 使用Mark专属的计数器创建行 XSSFRow row = sheet_Mark.createRow(markRowCounter); row.createCell(0).setCellValue(id_Values); row.createCell(1).setCellValue(name_Values); row.createCell(2).setCellValue(age_Values); // 添加完成后计数器加1,准备下一行 markRowCounter++; } else if(name_Values.equals("John")){ // 使用John专属的计数器创建行 XSSFRow row = sheet_John.createRow(johnRowCounter); row.createCell(0).setCellValue(id_Values); row.createCell(1).setCellValue(name_Values); row.createCell(2).setCellValue(age_Values); // 添加完成后计数器加1 johnRowCounter++; } }
扩展性优化(可选)
如果以后需要支持更多名字,用Map来存储工作表和对应的计数器会更灵活,不用每次加名字都修改循环里的条件:
// 提前初始化工作表和行计数器的映射 Map<String, XSSFSheet> sheetMap = new HashMap<>(); Map<String, Integer> rowCounterMap = new HashMap<>(); sheetMap.put("Mark", workbook.createSheet("Mark")); sheetMap.put("John", workbook.createSheet("John")); rowCounterMap.put("Mark", 0); rowCounterMap.put("John", 0); for(int i = 0; i < jTable1.getRowCount(); i++){ Integer id_Values = (int) jTable1.getValueAt(i,0); String name_Values = (String) jTable1.getValueAt(i, 1); Integer age_Values = (int) jTable1.getValueAt(i,2); // 检查当前名字是否有对应的工作表 if(sheetMap.containsKey(name_Values)){ XSSFSheet targetSheet = sheetMap.get(name_Values); int currentRow = rowCounterMap.get(name_Values); XSSFRow row = targetSheet.createRow(currentRow); row.createCell(0).setCellValue(id_Values); row.createCell(1).setCellValue(name_Values); row.createCell(2).setCellValue(age_Values); // 更新计数器 rowCounterMap.put(name_Values, currentRow + 1); } }
这样修改后,你的两个工作表都会从第1行开始连续填充数据,不会再出现空白行啦!
内容的提问来源于stack exchange,提问作者Maibhalsych
相关产品推荐
相关产品推荐

