簡體   English   中英

Apache POI XSSFWorkbook setSheetOrder 未排序

[英]Apache POI XSSFWorkbook setSheetOrder not sorting

我正在使用 Apache POI (4.1.1) 修改現有工作簿。 該工作簿包含四張紙。 我通過克隆第二個工作表作為模板,然后將數據寫入新的克隆工作表。 它被克隆了大約六次。 在此過程結束時,我刪除了模板工作表,然后嘗試為所有工作表設置工作表順序:現有工作表(減去模板),然后是我克隆的工作表。 我正在使用 XSSFWorkbook::setSheetOrder 來執行此操作,並且我看到它在調試中更改了索引,但是當我的 Excel 文件實際寫出時,工作表沒有按順序排列。

這是相關的代碼:

        // wb is an XSSFWorkbook
        wb.removeSheetAt(wb.getSheetIndex("Original Sheet 2")); // Remove the template sheet
        wb.setSheetOrder("Original Sheet 1", 0);
        for (ReportPresenter presenter : dataMap.values()) {
            String sheetTitle = makeSheetTitleFromPresenter(presenter);
            int oldIndex = wb.getSheetIndex(wb.getSheet(sheetTitle));
            wb.setSheetOrder(sheetTitle, presenter.getAnalysisNumber());
            int newIndex = wb.getSheetIndex(wb.getSheet(sheetTitle));
            System.out.println(oldIndex + " -> " + newIndex);
        }
        wb.setSheetOrder("Original Sheet 3", dataMap.size() + 1);
        wb.setSheetOrder("Original Sheet 4", dataMap.size() + 2);

我在上面包含了調試 println 以在這里展示我如何知道索引實際上正在使用 setSheetOrder 方法更改為我想要的順序。 但是,當我打開此代碼生成的 Excel 文件時,我的工作表都存在,但它們沒有按照我指定的順序排列。

我真的很感激一些想法! 謝謝你。

無法重現該行為。 請展示一個最小的、可重現的示例,以顯示該行為。

我將提供一個這樣的,它表明它可以正常工作:

像這樣從Execl.xlsx開始:

在此處輸入圖片說明

然后如下代碼:

import java.io.FileOutputStream;
import java.io.FileInputStream;

import org.apache.poi.xssf.usermodel.*;

public class ExcelSetSheetOrder {

 public static void main(String[] args) throws Exception {

  java.util.Map<Integer, ReportPresenter> dataMap = new java.util.HashMap<Integer, ReportPresenter>();
  dataMap.put(1, new ReportPresenter("New Sheet 1", 1));
  dataMap.put(2, new ReportPresenter("New Sheet 2", 2));
  dataMap.put(3, new ReportPresenter("New Sheet 3", 3));
  dataMap.put(4, new ReportPresenter("New Sheet 4", 4));
  dataMap.put(5, new ReportPresenter("New Sheet 5", 5));
  dataMap.put(6, new ReportPresenter("New Sheet 6", 6));

  try (XSSFWorkbook workbook = new XSSFWorkbook(new FileInputStream("./Excel.xlsx"))) {

   workbook.cloneSheet(workbook.getSheetIndex("Original Sheet 2"), dataMap.get(1).getSheetTitle());
   workbook.cloneSheet(workbook.getSheetIndex("Original Sheet 2"), dataMap.get(2).getSheetTitle());
   workbook.cloneSheet(workbook.getSheetIndex("Original Sheet 2"), dataMap.get(3).getSheetTitle());
   workbook.cloneSheet(workbook.getSheetIndex("Original Sheet 2"), dataMap.get(4).getSheetTitle());
   workbook.cloneSheet(workbook.getSheetIndex("Original Sheet 2"), dataMap.get(5).getSheetTitle());
   workbook.cloneSheet(workbook.getSheetIndex("Original Sheet 2"), dataMap.get(6).getSheetTitle());

   workbook.removeSheetAt(workbook.getSheetIndex("Original Sheet 2")); // Remove the template sheet
   workbook.setSheetOrder("Original Sheet 1", 0);
   for (ReportPresenter presenter : dataMap.values()) {
    String sheetTitle = presenter.getSheetTitle();
    int oldIndex = workbook.getSheetIndex(workbook.getSheet(sheetTitle));
    workbook.setSheetOrder(sheetTitle, presenter.getAnalysisNumber());
    int newIndex = workbook.getSheetIndex(workbook.getSheet(sheetTitle));
    System.out.println(oldIndex + " -> " + newIndex);
   }
   workbook.setSheetOrder("Original Sheet 3", dataMap.size() + 1);
   workbook.setSheetOrder("Original Sheet 4", dataMap.size() + 2);

   String filePath = "./ExcelNew.xlsx";
   try (FileOutputStream fileOut = new FileOutputStream(filePath)) {
    workbook.write(fileOut);
   }
  }
 }

 static class ReportPresenter {
  String sheetTitle = "";
  int analysisNumber = -1;

  public ReportPresenter(String sheetTitle, int analysisNumber) {
   this.sheetTitle = sheetTitle;
   this.analysisNumber = analysisNumber;
  }

  public int getAnalysisNumber() {
   return this.analysisNumber;
  }
  public String getSheetTitle() {
   return this.sheetTitle;
  }
 }
}

在控制台上打印以下內容:

axel@arichter:~/Dokumente/JAVA/poi/poi-4.1.1$ javac -Xlint:deprecation -Xlint:unchecked -cp .:./*:./lib/*:./ooxml-lib/* ExcelSetSheetOrder.java 
axel@arichter:~/Dokumente/JAVA/poi/poi-4.1.1$ java -cp .:./*:./lib/*:./ooxml-lib/* ExcelSetSheetOrder 
3 -> 1
4 -> 2
5 -> 3
6 -> 4
7 -> 5
8 -> 6

並導致此結果ExcelNew.xlsx

在此處輸入圖片說明

事實證明,我對 XSSFWorkbook::setSheetOrder 的工作方式有誤解。

我假設(錯誤地)設置工作表的順序會使工作表保持在那個位置,有點像將工作表插入到數組的索引中。 但是,如果您最近的調用隱式修改了上次調用中使用的工作表前面的順序,則對 setSheetOrder 的后續調用將修改其他工作表的工作表順序。

例如,如果您有這樣訂購的工作表:

[StaticX, StaticY, Cloned3, Cloned4, Cloned1, Cloned2] 然后你調用 setSheetOrder("Cloned3", 3)

訂單變成

[StaticX, StaticY, Cloned4, Cloned3, Cloned1, Cloned2] 這是需要的。

但是,對 setSheetOrder("Cloned1", 1) 的后續調用現在將使訂單

[StaticX, Cloned1, StaticY, Cloned4, Cloned3, Cloned2] 已將 Cloned3 移出位置 3。

在我的調試打印中,我認為它正在工作,因為我只是檢查最后一次調用設置的順序,這當然每次都是正確的,但是當我在每次設置工作表順序后開始打印所有工作表的順序時,問題變得很明顯。

為了解決這個問題,我只是按照我想要的順序將我所有的工作表名稱放入一個數組中,並按順序設置工作表的順序,這很好用。

非常感謝 Axel 提供了這個最小的例子。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM