首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> Java 程式設計 >> Java 程式設計入門

Java 操作 Excel 實戰:JCOM + JXL 組件調用全流程指南(含資源釋放避坑)

     編輯:Java 程式設計入門

環境準備:四大必備組件

  • jdom-1.0.jar
  • jxl-2.5.5.jar (純 Java 讀寫 Excel)
  • jcom-2.2.4.jar (Java-COM 橋接)
  • jcom.dll **必須放入 JDK bin 目錄或系統 System32** (推薦 JDK 目錄,避免污染系統)

核心對象模型

ReleaseManager rm = new ReleaseManager();          // COM 組件容器,管理生命週期
IDispatch xlsApp = new IDispatch(rm, "Excel.Application"); // Excel Application 對象
// 所有 COM 對象均表現為 IDispatch,操作均拋出 JComException

完整操作流程(含關鍵細節)

1. 打開工作簿

IDispatch workbooks = (IDispatch) xlsApp.get("Workbooks");
xlsApp.put("Visible", new Boolean(false));           // 後台運行
IDispatch workbook = (IDispatch) workbooks.method("open", new Object[]{ filePath });

2. 另存為 (格式 9 = Excel 97-2003)

File f = new File(outPath);
if (f.exists()) f.delete();
workbook.method("saveAs", new Object[]{ outPath, new Integer(9) });

3. 遍歷工作表

IDispatch sheets = (IDispatch) workbook.get("Sheets");
int count = Integer.parseInt(sheets.get("Count").toString());
// ⚠️ Excel 索引從 1 開始!
for (int i = 1; i <= count; i++) {
    IDispatch sheet = (IDispatch) sheets.get("Item", new Object[]{ new Integer(i) });
    // 或按名稱:sheets.get("Item", new Object[]{ sheetName })
    String name = sheet.get("Name").toString();
}

4. 獲取行列數

類型代碼說明
總行數 (65536)sheet.get("Rows").get("Count")含空行
總列數 (256)sheet.get("Columns").get("Count")含空列
已用區域行數sheet.get("UsedRange").get("Rows").get("Count")實際數據範圍
已用區域列數sheet.get("UsedRange").get("Columns").get("Count")實際數據範圍

5. 讀取單元格數據 (索引同樣從 1 開始)

for (int r = 1; r <= rows; r++) {
    for (int c = 1; c <= cols; c++) {
        IDispatch cell = (IDispatch) sheet.get("Cells", new Object[]{ new Integer(r), new Integer(c) });
        String val  = cell.get("Value").toString();        // 數值型會帶 .0 (如 1 → "1.0")
        String txt  = cell.get("Text").toString();         // 顯示文本原樣
        boolean hasF = Boolean.parseBoolean(cell.get("HasFormula").toString());
        String formula = cell.get("FormulaR1C1").toString(); // R1C1 風格公式
    }
}

6. 工作表保護與解除

IDispatch activeSheet = (IDispatch) xlsApp.get("ActiveSheet");
// 保護:密碼、保護繪圖對象、保護內容
activeSheet.method("Protect", new Object[]{ pwd, Boolean.TRUE, Boolean.TRUE });
// 解除
activeSheet.method("Unprotect", new Object[]{ pwd });

資源釋放:防止 Excel 進程殭屍的關鍵

**必須在 finally 塊中按逆序釋放,且不可省略 ReleaseManager.release()**

finally {
    try {
        if (workbook != null) {
            workbook.method("close", new Object[]{ Boolean.FALSE }); // 不保存關閉
            workbook = null;
        }
        if (xlsApp != null) {
            xlsApp.put("Saved", Boolean.TRUE);        // 標記已存,避免彈窗
            xlsApp.method("quit", null);              // 退出 Excel 進程
            xlsApp = null;
        }
    } finally {
        if (rm != null) {
            rm.release();      // 釋放底層 COM 資源,關鍵!
            rm = null;
        }
    }
}
  • workbook.close() 僅關閉工作簿;xlsApp.quit() 才退出 Excel.exe 進程。
  • 漏掉 rm.release() 會導致 EXCEL.EXE 殘留進程,佔用內存並鎖定文件。
  • 雙層 finally 確保即使 COM 調用拋異常也能釋放資源。

JXL 純 Java 方案對比

JXL (jxl.jar) 無需 COM、無需 Excel 安裝、跨平台、性能較好,但**不支持 .xlsx (Excel 2007+)**、不支持圖表/宏/樞紐表、樣式控制弱。JCOM 適合需完整 Excel 功能、Windows 環境、可接受進程開銷的場景。現代項目推薦 Apache POI (支持 .xls/.xlsx、功能全、純 Java)。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved