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

Apache poi XLSX到XLS

滑骞尧
2023-03-14

我正在使用apache poi,我读取一些xlsx文件,对其进行处理,然后将其导出为xlsx格式。但现在我要求导出格式为XLS(这是为了支持旧设备)。有没有一种简单的方法可以将代码生成的xlsx文件转换为xls

所有流程都是用XSSF实现的。

提前谢谢。

共有3个答案

程举
2023-03-14

我也遇到过同样的情况,并使用Java实现了以下将XLSX转换为XLS的代码

下面的代码将使用apache camel(来自路径的轮询文件)和apace poi从目录和进程中读取它

import java.io.BufferedOutputStream;
import java.io.File;
import java.io.FileOutputStream;
import java.io.InputStream;
import java.io.OutputStream;
import java.util.Iterator;
import java.util.Optional;

import org.apache.camel.Exchange;
import org.apache.camel.Processor;
import org.apache.poi.hssf.usermodel.HSSFWorkbook;
import org.apache.poi.ss.usermodel.Cell;
import org.apache.poi.ss.usermodel.CellStyle;
import org.apache.poi.ss.usermodel.Row;
import org.apache.poi.ss.usermodel.Sheet;
import org.apache.poi.ss.usermodel.Workbook;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Component;

@Component
public class ExcelFileProcessor implements Processor {
    final Logger logger = LoggerFactory.getLogger(getClass());
    
    @Value("${test.dir.in}")
    private String inDir;
    
    @Override
    public void process(Exchange exchange) throws Exception {
        logger.info("Entry-ExcelFileProcessor- Process method");
        long start = System.currentTimeMillis();
        
        String fileNameWithExtn=(String) exchange.getIn().getHeader("camelFileName");
        Long originalFileSize = (Long) exchange.getIn().getHeader("CamelFileLength");
        String fileNameWithOutExtn = fileNameWithOutExtn(fileNameWithExtn);
        
        logger.info("fileNameWithExtn:{}" ,fileNameWithExtn);
        logger.info("fileNameWithOutExtn:{}" ,fileNameWithOutExtn);
        logger.info("originalFileSize:{}" ,originalFileSize);
        
        try(InputStream in = exchange.getIn().getBody(InputStream.class);
            XSSFWorkbook wbIn = new XSSFWorkbook(in);
            Workbook wbOut = new HSSFWorkbook();) {
            
          int sheetCnt = wbIn.getNumberOfSheets();
          for (int i = 0; i < sheetCnt; i++) {
              Sheet sIn = wbIn.getSheetAt(0);
              Sheet sOut = wbOut.createSheet(sIn.getSheetName());
              Iterator<Row> rowIt = sIn.rowIterator();
              while (rowIt.hasNext()) {
                  Row rowIn = rowIt.next();
                  Row rowOut = sOut.createRow(rowIn.getRowNum());

                  Iterator<Cell> cellIt = rowIn.cellIterator();
                  while (cellIt.hasNext()) {
                      Cell cellIn = cellIt.next();
                      Cell cellOut = rowOut.createCell(cellIn.getColumnIndex(), cellIn.getCellType());

                      switch (cellIn.getCellType()) {
                      case Cell.CELL_TYPE_BLANK: break;

                      case Cell.CELL_TYPE_BOOLEAN:
                          cellOut.setCellValue(cellIn.getBooleanCellValue());
                          break;

                      case Cell.CELL_TYPE_ERROR:
                          cellOut.setCellValue(cellIn.getErrorCellValue());
                          break;

                      case Cell.CELL_TYPE_FORMULA:
                          cellOut.setCellFormula(cellIn.getCellFormula());
                          break;

                      case Cell.CELL_TYPE_NUMERIC:
                          cellOut.setCellValue(cellIn.getNumericCellValue());
                          break;

                      case Cell.CELL_TYPE_STRING:
                          cellOut.setCellValue(cellIn.getStringCellValue());
                          break;
                      }
                      CellStyle styleIn = cellIn.getCellStyle();
                      CellStyle styleOut = cellOut.getCellStyle();
                      styleOut.setDataFormat(styleIn.getDataFormat());
                      cellOut.setCellComment(cellIn.getCellComment());
                     }
              }
          }
          File outF = new File(inDir+fileNameWithOutExtn+".xls");
          try(OutputStream out = new BufferedOutputStream(new FileOutputStream(outF));){
              wbOut.write(out);
          }
      }catch (Exception e) {
            logger.info("Error during Excel file process:{}",e.getMessage());
      }
        long end = System.currentTimeMillis();
        logger.info("Total time processed for file in - {} ms", (end - start));
        logger.info("Exit-FileProcessor- Process method");
     }
    public String fileNameWithOutExtn(String fileName) {
        return Optional.of(fileName.lastIndexOf('.')).filter(i-> i >= 0)
                .map(i-> fileName.substring(0, i)).orElse(fileName);
    }
}

如果您不使用camel并想从以下片段的文件使用中获取输入流

    String inpFn = "input.xlsx"; 
    String outFn = "output.xls"; 

    InputStream in = new BufferedInputStream(new FileInputStream(inpFn));
    try {
        Workbook wbIn = new XSSFWorkbook(in);
        File outF = new File(outFn);
        if (outF.exists())
            outF.delete();

        Workbook wbOut = new HSSFWorkbook();
        //continue with above code
解翰采
2023-03-14

您需要切换到“ss”实现,它允许透明地使用HSSF(=XLS)和XSSF(=XSLX),有关原始HSSF的一些详细信息,请参阅http://poi.apache.org/spreadsheet/converting.html-

然后只需要HSSFWorkbook/XSSFWorkbook的两个构造函数来决定要生成两种格式中的哪一种。

董高逸
2023-03-14

我同意正确的答案,但我想添加几行代码。

您说过您正在使用XSSF实现。

因此,对于要保存的工作簿,请执行以下更改:changeXSSFWorkbook x=new XSSFWorkbook() 至<代码>工作簿x=新建HSSF工作簿() 从组织导入工作簿的位置。阿帕奇。poi。不锈钢。用户模型。工作手册

类似地,更改XSSFRow实例化

XSSFRow r = newXSSF();

至第r行=新HSSFRow() 并从组织导入行。阿帕奇。poi。不锈钢。用户模型。世界其他地区

同样,将单元格实例化更改为ss。usermodel包。

最后将HSSF工作簿保存为。xls扩展。

 类似资料:
  • 问题内容: 在PHP中,将RGB三元组转换为HSV值的最直接方法是什么? 问题答案:

  • 问题内容: 对于正在编写的程序,我正在使用base64.b64encode(f.read(image))从一台计算机上传输图像,并尝试在接收脚本中读取它而不将其保存到硬盘驱动器中(以最大程度地减少这种情况)处理时间)。我很难弄清楚如何将图像读取到OpenCV中而不将其保存在本地。 这是我发送图像的代码如下所示: 同时,这是接收它的代码。(这在on_message函数中,因为我正在使用MQTT进行传

  • 签到开关状态 获取签到信息 签到 累计签到排行榜 新版签到 签到开关状态 签到应用具有开关性质,管理员可从后台控制签到是否被开启或者关闭,而开关会在「启动信息」接口中提供。提供格式如下: { "checkin": true // Or "checkin": false } 签到金额格式: { "checkin:attach_balance": 0 } 金额为0时表示未配置 但是

  • 实时了解外勤人员位置活动轨迹及分布,出差也可以异地打卡。 开始你的第一次签到 如何签到 打开手机钉钉-工作-签到 签到按钮自动生成签到时间及签到地点 拍照自带时间和地点水印,提交完成签到 签到设置 根据公司要求选择签到相关设置 查看足迹 签到足迹 ● 点击右下角足迹,直观查看团队足迹,根据部门和日期筛选历史签到记录 ● 选择未签到,可以查看未签到人员,对未签到人员Ding一下 ● 点击足迹分布,可

  • 在上课页面的右下侧点击“活动-签到” 选择签到时间(一般为上课时间),点击"开启签到"。 页面跳转,实时显示目前签到人数,并可随时关闭签到。**

  • 我们添加了使用log4J 2的库。X,但我们仍在使用log4J 1。X(主要是因为我们有自己的一些应用程序和记录仪)。我被告知解决方案是发送log4J 2。x到slf4j(使用log4j-to-slf4j,版本2。X),然后slf4j到log4J 1。X,使用slf4j-log4j12,版本1。X. 这就是我刚才所做的,但我仍然得到以下信息: ERROR StatusLogger未找到log4j2