如何使用Apache POI更新单元格引用值

时间:2013-07-11 07:10:01

标签: java apache-poi

在更新某些值后,我正在使用Apache POI从现有的XSSFWorkbook创建新的XSSFWorkbook。假设我现有的工作簿中有两个工作表(比方说:工作表A和B)。工作表B具有来自工作表A的一些单元格引用。如果我修改工作表A的那些单元格值并将它们另存为新工作簿,则工作表B的相应单元格值也应该更新。但事实并非如此。我如何以编程方式更新它们? 。谢谢。

我的代码:

public  void createExcel(ClientData cd) throws FileNotFoundException, IOException, InvalidFormatException{
            // create a new file
        double[] dataHolder1= cd.getFinalData1(),  param1 = cd.getRecord1Param();
        double[] dataHolder2 = cd.getFinalData2(), param2 = cd.getRecord2Param();
        double[] ncv = cd.getNcv();
        String[] pname = cd.getName();
            Workbook workbook = new XSSFWorkbook(OPCPackage.open(new FileInputStream("template/mncv.xlsx"))); // or sample.xls
            //CreationHelper createHelper = workbook.getCreationHelper();
            Sheet s=workbook.getSheetAt(0);

            int counter = dataHolder1.length + param1.length +param2.length+dataHolder2.length;//+ param1.length + param2.length;
//            r = s.getRow(0);
//            r.getCell(0).setCellValue("Param1");
//            r.getCell(1).setCellValue("Record1");
//            r.getCell(2).setCellValue("Param2");
//            r.getCell(3).setCellValue("Record2");

            int i;
            for(i=0;i<counter;i++){
                if(i<param1.length){
                    for(int j=0;j<param1.length;j++){
                        r = s.getRow(i);
                        r.getCell(0).setCellValue(param1[j]);
                        i++;
                    }
                }else if(i<dataHolder1.length+param1.length && i>=param1.length){

                    for(int j=0;j<dataHolder1.length;j++){
                        r = s.getRow(i);
                        r.getCell(0).setCellValue(dataHolder1[j]);
                        i++;
                    }

                }else if(i<dataHolder1.length+param1.length+param2.length && i>=dataHolder1.length+param1.length){
                    for(int j=0;j<param2.length;j++){
                        r = s.getRow(i);
                        r.getCell(0).setCellValue(param2[j]);
                        i++;
                    }
                }else{
                    for(int j=0;j<dataHolder2.length;j++){
                        r = s.getRow(i);
                        r.getCell(0).setCellValue(dataHolder2[j]);
                        i++;
                    }
                }

//                if(i<=param1.length){
//                    r.getCell(0).setCellValue(param1[i-1]);
//                    r.getCell(2).setCellValue(param2[i-1]);
//
//                }
                // r.getCell(0).setCellValue(param1[i]);
                 //r.getCell(3).setCellValue(dataHolder2[i-1]);
                i--;
            }
            for(int k=0;k<ncv.length;k++){
                r = s.getRow(i);
                r.getCell(0).setCellValue(ncv[k]);
                i++;
            }

            s = workbook.getSheetAt(1);

            s.getRow(2).getCell(5).setCellValue(pname[0]+" "+pname[1]+" "+pname[2]);
            s.getRow(3).getCell(5).setCellValue(cd.getAge());
            s.getRow(4).getCell(5).setCellValue(cd.getGender());


 try (FileOutputStream out = new FileOutputStream("workbook.xlsx")) { 
     //WorkbookEvaluator we = new WorkbookEvaluator(workbook); 

            workbook.write(out);     
            out.close();
          XSSFFormulaEvaluator.evaluateAllFormulaCells((XSSFWorkbook) workbook);

        }catch(Exception e){
            System.out.println(e);
        }

3 个答案:

答案 0 :(得分:2)

Excel文件格式缓存公式评估的结果,以便更快地打开文件。这意味着当您对文件进行更改后,您需要评估所有公式单元格以更新其缓存值。 (否则,当您在Excel中加载文件时,几乎所有情况下它都会显示旧值,直到您进入该单元格)

幸运的是,Apache POI提供了执行此操作的代码,有关详细信息,请参阅Formula Evaluation documentation。 (您可以选择仅重新计算某些公式,如果您只知道那些单元格已更改,或者执行所有操作)

答案 1 :(得分:0)

对于任何单元格,在运行时说“B5”,

cell.getReference(); 

会给你单元格引用(比如示例......它会返回“B5”)

cell.getReference().toString().charAt(0); 

将为您提供列参考(如果当前单元格为B5,将为您提供“B”)。现在

cell.getRowIndex(); 

OR      。cell.getReference()的toString()的charAt(1);

会给你行索引。现在你有了目标细胞的参考。只需将这些字符替换为您已创建的引用即可。这将更新单元格引用。

答案 2 :(得分:0)

以下解决方案对我有用

wb.setForceFormulaRecalculation(true);
// replace "wb" with your HSSFWorkbook/XSSFWorkbook object