【问题标题】:read excel file using Apache POI使用 Apache POI 读取 excel 文件
【发布时间】:2013-04-02 09:35:21
【问题描述】:

我创建了这段代码来使用 Apache POI 读取 excel 文件的内容。我使用 eclipse 作为编辑器,但是当我运行代码时,我在粗体字的行中遇到了问题。有什么问题? excel的内容如下:

Emp ID  Name    Salary

 1.0    john    2000000.0

 2.0    dean    4200000.0

 3.0    sam     2800000.0

 4.0    cass    600000.0

import java.io.*;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
import org.apache.poi.hssf.usermodel.HSSFCell;
import org.apache.poi.hssf.usermodel.HSSFRow;
import org.apache.poi.hssf.usermodel.HSSFSheet;
import org.apache.poi.hssf.usermodel.HSSFWorkbook;
import org.apache.poi.poifs.filesystem.POIFSFileSystem;



public class ExcelRead {

public static void main(String[] args) throws Exception {
    File excel = new File ("C:\\Users\\Efi\\Documents\\test.xls");
    FileInputStream fis = new FileInputStream(excel);

    HSSFWorkbook wb = new HSSFWorkbook(fis);
    HSSFSheet ws = wb.getSheet("Input");

    int rowNum = ws.getLastRowNum()+1;
    int colNum = ws.getRow(0).getLastCellNum();
    String[][] data = new String[rowNum][colNum];


    for (int i=0; i<rowNum; i++){
        HSSFRow row = ws.getRow(i);
            for (int j=0; j<colNum; j++){
                HSSFCell cell = row.getCell(j);
                String value = cellToString(cell);
                data[i][j] = value;
                System.out.println("The value is" + value);

            }
       }
    }

public static String cellToString (HSSFCell cell){

int type;
Object result;
type = cell.getCellType();

    switch(type) {


    case 0://numeric value in excel
        result = cell.getNumericCellValue();
        break;
    case 1: //string value in excel
        result = cell.getStringCellValue();
        break;
    case 2: //boolean value in excel
        result = cell.getBooleanCellValue ();
        break;
    default:
        ***throw new RunTimeException("There are not support for this type of               
       cell");***
        }

return result.toString();
}

}

【问题讨论】:

  • 问题出在这里: throw new RunTimeException("There are not support for this type of cell");

标签: java apache-poi


【解决方案1】:

除了您在switch 语句中捕获的那些之外,还有additional cell types。您有 0 (CELL_TYPE_NUMERIC)、1 (CELL_TYPE_STRING) 和 2 的案例,但 2CELL_TYPE_FORMULA。以下是其他可能的值:

  • 3:CELL_TYPE_BLANK
  • 4:CELL_TYPE_BOOLEAN
  • 5:CELL_TYPE_ERROR

在你的 switch 语句中使用 Cell 常量来代替整数字面量的单元格类型,并使用所有 6 个常量来捕获所有可能的情况。

正如@Vash 已经建议的那样,在您的RuntimeException 消息中包含实际的单元格type

【讨论】:

    【解决方案2】:

    检查我创建的this library,用于轻松读取 XLSX、XLS 和 CSV 文件。它使用 Apache POI 处理 excel 文件,并根据您的配置将 excel 行转换为 Java bean 列表。

    这是一个例子:

    RowConverter<Country> converter = (row) -> new Country(row[0], row[1]);
    
    ExcelReader<Country> reader = ExcelReader.builder(Country.class)
         .converter(converter)
         .withHeader()
         .csvDelimiter(';')
         .sheets(1)
         .build();
    
    List<Country> list;
    list = reader.read("src/test/resources/CountryCodes.xlsx");
    list = reader.read("src/test/resources/CountryCodes.xls");
    list = reader.read("src/test/resources/CountryCodes.csv");
    

    使用以下 excel 和 bean 文件:

    public static class Country {
      public String shortCode;
      public String name;
    
      public Country(String shortCode, String name) {
        this.shortCode = shortCode;
        this.name = name;
      }
    }
    

    Excel:

        Code    Country
    ad  Andorra
    ae  United Arab Emirates
    af  Afghanistan
    ag  Antigua and Barbuda
    ...
    

    【讨论】:

      【解决方案3】:

      使用 XSSFWorkbook 和 XSSFSheet 并没有帮助我阅读 .xls,但我使用了这段代码,它帮助我阅读了 .xls 和 xlsx 文件:

        public static void readExcelFile(File file) throws IOException, InvalidFormatException {
      Workbook workbook = WorkbookFactory.create(new File(file.toString()));
              Integer sheet = workbook.getNumberOfSheets();
              DataFormatter dataFormatter = new DataFormatter();
              for (int i = 0; i < sheet; i++) {
                  Sheet s = workbook.getSheetAt(i);
                  Iterator<Row> rowIterator = s.rowIterator();
                  while (rowIterator.hasNext()) {
                      Row row = rowIterator.next();
                      Iterator<Cell> cellIterator = row.cellIterator();
                      while (cellIterator.hasNext()) {
                          Cell cell = cellIterator.next();
                          printCellValue(cell);
                          // both work perfect
                          // printCellValue(cell);
                          /*String cellValue = dataFormatter.formatCellValue(cell);
                          System.out.print(cellValue + "\t");*/
                      }
                      System.out.println();
                  }
      
              }
          }
      
      public static void printCellValue(Cell cell) {
              switch (cell.getCellType()) {
                  case Cell.CELL_TYPE_BOOLEAN:
                      System.out.print(cell.getBooleanCellValue());
                      break;
                  case Cell.CELL_TYPE_STRING:
                      System.out.print(cell.getRichStringCellValue().getString());
                      break;
                  case Cell.CELL_TYPE_NUMERIC:
                      if (DateUtil.isCellDateFormatted(cell)) {
                          System.out.print(cell.getDateCellValue());
                      } else {
                          System.out.print(cell.getNumericCellValue());
                      }
                      break;
                  case Cell.CELL_TYPE_FORMULA:
                      System.out.print(cell.getCellFormula());
                      break;
                  case Cell.CELL_TYPE_BLANK:
                      System.out.print("  ");
                      break;
                  default:
                      System.out.print("");
              }
      
              System.out.print("\t");
          }
      

      【讨论】:

        【解决方案4】:

        您应该使用有关您的 switch 语句不支持的类型的信息来修改 RuntimeException。然后你就可以添加对它的支持,所以不会抛出异常。

        所以要查看你的程序正在做什么而不是

        throw new RunTimeException("There are not support for this type of cell");

        你应该添加

        throw new RunTimeException("There are not support for type with id ["+type+"] of cell");

        这将告诉您您错过了什么。如何处理这种情况取决于你。

        【讨论】: