当前位置: 首页 > 知识库问答 >
问题:

使用apache POI-FileNotFound读取excel 2003文件

杭志泽
2023-03-14

我正在写一些代码导入Excel文件到数据库。文件可能很大(数千行),所以我使用事件API。POI版本为3.9

我这样打开文件:FileInputStream fin=new FileInputStream(file);

//create record listener
HSSFRecordListener mainListener =  new HSSFRecordListener("aaa.xls");
// create a new org.apache.poi.poifs.filesystem.Filesystem
POIFSFileSystem poifs = new POIFSFileSystem(fin);
// get the Workbook (excel part) stream in a InputStream
din = poifs.createDocumentInputStream("Workbook");

有些文件在最后一行引发FileNotFoundException。的确,如果我用7zip打开那些文件,就没有workbook条目,而是有book

try {
    din = poifs.createDocumentInputStream("Workbook");
} catch (FileNotFoundException e) {
    try {
        din = poifs.createDocumentInputStream("Book");
    } catch (FileNotFoundException e1) {                    
        FileNotFoundException e2 = new FileNotFoundException("Neither Workbook nor Book found in file!");                    
        e2.initCause(e1);
        throw e2;
    }
}
org.springframework.web.util.NestedServletException: Request processing failed; nested exception is org.apache.poi.hssf.record.RecordFormatException: Unable to construct record instance
    org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:894)
    org.springframework.web.servlet.FrameworkServlet.doPost(FrameworkServlet.java:789)
    javax.servlet.http.HttpServlet.service(HttpServlet.java:647)
    javax.servlet.http.HttpServlet.service(HttpServlet.java:728)
    org.netbeans.modules.web.monitor.server.MonitorFilter.doFilter(MonitorFilter.java:393)
root cause

org.apache.poi.hssf.record.RecordFormatException: Unable to construct record instance
    org.apache.poi.hssf.record.RecordFactory$ReflectionConstructorRecordCreator.create(RecordFactory.java:65)
    org.apache.poi.hssf.record.RecordFactory.createSingleRecord(RecordFactory.java:301)
    org.apache.poi.hssf.record.RecordFactoryInputStream$StreamEncryptionInfo.<init>(RecordFactoryInputStream.java:65)
    org.apache.poi.hssf.record.RecordFactoryInputStream.<init>(RecordFactoryInputStream.java:182)
    org.apache.poi.hssf.eventusermodel.HSSFEventFactory.genericProcessEvents(HSSFEventFactory.java:139)
    org.apache.poi.hssf.eventusermodel.HSSFEventFactory.processEvents(HSSFEventFactory.java:106)
    pl.veracomp.service.SpreadsheetImportService.process(SpreadsheetImportService.java:369)
    pl.veracomp.controller.uploadController.onSubmit(uploadController.java:57)
    org.springframework.web.servlet.mvc.SimpleFormController.processFormSubmission(SimpleFormController.java:272)
    org.springframework.web.servlet.mvc.AbstractFormController.handleRequestInternal(AbstractFormController.java:268)
    org.springframework.web.servlet.mvc.AbstractController.handleRequest(AbstractController.java:153)
    org.springframework.web.servlet.mvc.SimpleControllerHandlerAdapter.handle(SimpleControllerHandlerAdapter.java:48)
    org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:923)
    org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.java:852)
    org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:882)
    org.springframework.web.servlet.FrameworkServlet.doPost(FrameworkServlet.java:789)
    javax.servlet.http.HttpServlet.service(HttpServlet.java:647)
    javax.servlet.http.HttpServlet.service(HttpServlet.java:728)
    org.netbeans.modules.web.monitor.server.MonitorFilter.doFilter(MonitorFilter.java:393)
root cause

org.apache.poi.hssf.record.RecordFormatException: Not enough data (0) to read requested (2) bytes
    org.apache.poi.hssf.record.RecordInputStream.checkRecordPosition(RecordInputStream.java:216)
    org.apache.poi.hssf.record.RecordInputStream.readShort(RecordInputStream.java:233)
    org.apache.poi.hssf.record.InterfaceHdrRecord.<init>(InterfaceHdrRecord.java:43)
    sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
    sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:39)
    sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:27)
    java.lang.reflect.Constructor.newInstance(Constructor.java:513)
    org.apache.poi.hssf.record.RecordFactory$ReflectionConstructorRecordCreator.create(RecordFactory.java:57)
    org.apache.poi.hssf.record.RecordFactory.createSingleRecord(RecordFactory.java:301)
    org.apache.poi.hssf.record.RecordFactoryInputStream$StreamEncryptionInfo.<init>(RecordFactoryInputStream.java:65)
    org.apache.poi.hssf.record.RecordFactoryInputStream.<init>(RecordFactoryInputStream.java:182)
    org.apache.poi.hssf.eventusermodel.HSSFEventFactory.genericProcessEvents(HSSFEventFactory.java:139)
    org.apache.poi.hssf.eventusermodel.HSSFEventFactory.processEvents(HSSFEventFactory.java:106)
    pl.veracomp.service.SpreadsheetImportService.process(SpreadsheetImportService.java:369)
    pl.veracomp.controller.uploadController.onSubmit(uploadController.java:57)
    org.springframework.web.servlet.mvc.SimpleFormController.processFormSubmission(SimpleFormController.java:272)
    org.springframework.web.servlet.mvc.AbstractFormController.handleRequestInternal(AbstractFormController.java:268)
    org.springframework.web.servlet.mvc.AbstractController.handleRequest(AbstractController.java:153)
    org.springframework.web.servlet.mvc.SimpleControllerHandlerAdapter.handle(SimpleControllerHandlerAdapter.java:48)
    org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:923)
    org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.java:852)
    org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:882)
    org.springframework.web.servlet.FrameworkServlet.doPost(FrameworkServlet.java:789)
    javax.servlet.http.HttpServlet.service(HttpServlet.java:647)
    javax.servlet.http.HttpServlet.service(HttpServlet.java:728)
    org.netbeans.modules.web.monitor.server.MonitorFilter.doFilter(MonitorFilter.java:393)

可以在Excel2007中成功打开相同的文件。当我用save as=>Excel 97/2003手动保存它们时,7zip显示book条目已替换为workbook并且我可以用Apache POI成功地导入它们。

有人发现这个问题了吗?如何解决这个问题?

编辑

共有1个答案

微生阳平
2023-03-14

在您提出问题时,Apache POI没有其他解决方案。好消息是现在有了!

在Apache POI的新版本中,如果使用这些旧文件之一调用HSSFWorkbookWorkbookFactory,您将得到更有帮助的OldExcelFormatException

如果您想从这些文件中获取一些信息,那么OldExcelExtractor可以从包括Excel95(以及更早的版本)在内的格式中获取文本和数字。

 类似资料:
  • 介绍 在标准的ExcelReader中,如果数据量较大,读取Excel会非常缓慢,并有可能造成内存溢出。因此针对大数据量的Excel,Hutool封装了event模式的读取方式。 Excel03SaxReader只支持Excel2003格式的Sax读取。 使用 定义行处理器 首先我们实现一下RowHandler接口,这个接口是Sax读取的核心,通过实现handle方法编写我们要对每行数据的操作方式

  • 我有一个巨大的excel文件,其中包含大量列,如下所示:- 当我打印excel中的所有值时,我的代码生成的输出是:- 所以,如果我们看看上面的输出,我们可以注意到我留下空白值的单元格没有被POI库拾取。有没有一种方法可以让这些值为空?还是一种识别所呈现的值跳过空白单元格的方法? 请注意:我使用的不是usermodel(org.apache.poi.ss.usermodel),而是一个事件API来处

  • 我正在写一个程序,它需要从excel文件中读取和写入数据,而不考虑格式(xls或xlsx)。 我知道ApachePOI,但它似乎有不同的类来处理xls文件(HSSF)和xlsx(XSSF)文件。 任何人都知道我将如何实现我在这里的目标。(也欢迎使用POI以外的API的想法)。

  • 我是编程界的新手。嗯,我正在尝试使用ApachePOI库读取excel文件(5行5列)。我实际上有两个相同问题的实现。在第一个代码片段中,我只是读取excel文件并将其打印到控制台中。 然而,现在我正试图将读取的excel数据保存到一个数组中。所以我想在动态获取excel行和列大小后设置数组大小。但令我惊讶的是,当我执行第二个代码段时,似乎“while(cellIterator.hasNext()

  • 嗨,我想在第一行搜索一个字符串,如果找到了,我想移动那一列。

  • 我使用OpenCSV进行CSV文件的读写。在I hsd安装早期版本的Java(即Java 6)之前,它工作得很好。安装完之后,我的代码就停止工作了: 线程“main”java.lang.UnsupportedClassVersionError:COM/OpenCSV/CSVReader:不支持Major.Minor版本51.0在java.lang.ClassLoader.DefineClass1(