java去掉excel空行報錯
阿新 • • 發佈:2021-01-26
功能需求:
傳入一個excel,刪除其中所有空行,返回新的excel
出現問題:
刪除空行後的檔案,可以正常開啟,但是接下的程式碼處理會報錯:
Invalid column index (-1). Allowable column range for BIFF8 is (0..255) or (‘A‘..‘IV‘) xxxxxx 異常
除錯報錯程式碼,發現程式碼處理excel時,sheet的row數目與實際的數量不一致。
原本excel資料:
去掉空行後的excel:
但是處理後的excel,sheet頁物件的row資料還有4行,並不是看到的2行。
初步判斷還有兩個空行沒過濾掉
解決程式碼
/** * @param firstRow 從第幾行開始檢測空行 * @param inPutFilePath 檔案路徑 * @param outPutFilePath 檔案寫出路徑 * @return void * @throws * @Author hxh * @Date 2021-01-25 16:32:16 * @Desc: 去除excel裡的空行 */ public static void trimExcel(int firstRow, String inPutFilePath, String outPutFilePath) { Workbook wb = null; if (inPutFilePath == null) { return; } String extString = inPutFilePath.substring(inPutFilePath.lastIndexOf(".")); InputStream is = null; try { is = new FileInputStream(inPutFilePath); if (extString.equals(".xls")) { wb = new HSSFWorkbook(is); } else if (".xlsx".equals(extString)) { wb = new XSSFWorkbook(is); } else { wb = null; } } catch (FileNotFoundException e) { e.printStackTrace(); } catch (IOException e) { e.printStackTrace(); } finally { if (is != null) { try { is.close(); } catch (IOException e) { e.printStackTrace(); } } } Sheet sheet = null; Row row = null; String cellData = null; boolean empty = true; int useRows = firstRow; if (wb != null) { //獲取第一個sheet sheet = wb.getSheetAt(0); //獲取最大行數 從0開始算 int rownum = Math.max(sheet.getLastRowNum(),sheet.getPhysicalNumberOfRows())+1; //獲取最大列數 int colnum = 0; for (int i = firstRow; i < rownum; i++) { row = sheet.getRow(i); if (row != null) { colnum = Math.max( row.getLastCellNum(),row.getPhysicalNumberOfCells()); empty = true; for (int j = 0; j < colnum; j++) { cellData = (String) getCellFormatValue(row.getCell(j)); if (StringUtils.isNotBlank(cellData)) { empty = false; useRows++; break; } } if (empty) { sheet.removeRow(row); sheet.shiftRows(i + 1, rownum, -1); i--; rownum--; } } else { sheet.shiftRows(i + 1, rownum, -1); i--; rownum--; } } // rownum = sheet.getPhysicalNumberOfRows(); // begin 這是個大坑!!!程式碼後來才加上去的 rownum = Math.max(sheet.getLastRowNum(),sheet.getPhysicalNumberOfRows()); for (int i=useRows;i<rownum;i++){ row = sheet.getRow(i); sheet.removeRow(row); } // end 這是個大坑!!!程式碼後來才加上去的 FileOutputStream out = null; try { out = new FileOutputStream(outPutFilePath); wb.write(out); out.flush(); } catch (IOException e) { e.printStackTrace(); } finally { try { if (out != null) out.close(); } catch (IOException e) { e.printStackTrace(); } } } }
注意:
去掉空行後,除錯發現
sheet.getPhysicalNumberOfRows();結果是4
sheet.getLastRowNum(); 結果是2
大坑,按照解釋:
getPhysicalNumberOfRows()獲取的是物理行數,也就是不包括那些空行(隔行)的情況。
getLastRowNum()獲取的是最後一行的編號(編號從0開始)。
原以為getLastRowNum 一定會大於getPhysicalNumberOfRows,但是實際卻不是,看到除錯結果也是一臉懵逼,不知道為什麼,知道的小夥伴可以解釋下。