springboot通过 EasyExcel.read()方法解析csv(excel)文件中的数据用list接收

springboot通过 EasyExcel.read()方法解析csv(excel)文件中的数据用list接收


文章目录


前言


一、EasyExcel是什么?

EasyExcel是阿里巴巴开源的一个excel处理框架,以使用简单、节省内存著称。

EasyExcel能大大减少占用内存的主要原因是在解析Excel时没有将文件数据一次性全部加载到内存中。

而是从磁盘上一行行读取数据,逐个解析。

EasyExcel采用一行一行的解析模式,并将一行的解析结果以观察者模式通知处理(AnalysisEventListener)。

二、使用步骤

1.引入库

代码如下(示例):

c 复制代码
<dependencies>
    <dependency>
        <groupId>com.alibaba</groupId>
        <artifactId>easyexcel</artifactId>
        <version>3.1.2</version>
    </dependency>
</dependencies>

2.接收数据的实体类

c 复制代码
@Data
@Builder
@AllArgsConstructor
@NoArgsConstructor
public class UserVO extends BaseEntity {


    @ExcelIgnore
    private Integer id;


    /**
     * 编码
     */
    @ExcelIgnore
    private String code;


    /**
     * 英文名
     */
    @ExcelProperty(value = "英文名")
    private String name;

    /**
     * 中文名
     */
    @ExcelProperty(value = "中文名")
    private String nameCn;

    /**
     * 数据类型
     */
    @ExcelProperty(value = "类型")
    private String type;

    /**
     * 长度
     */
    @ExcelProperty(value = "长度")
    private Integer length;


    /**
     * 性别(0:男,1:女)(字典值需单独处理)
     */
    @ExcelProperty(value = "性别",converter = ExcelDictConverter.class)
    private Integer sex;

}

3.处理字典值ExcelDictConverter

java 复制代码
public class ExcelDictConverter implements Converter<Integer> {

    @Override
    public Class<?> supportJavaTypeKey() {
        return Number.class;
    }

    @Override
    public CellDataTypeEnum supportExcelTypeKey() {
        return CellDataTypeEnum.NUMBER;
    }


    @Override
    public Integer convertToJavaData(ReadConverterContext<?> context) {
        ReadCellData<?> readCellData = context.getReadCellData();
        String stringValue = readCellData.getStringValue();
        if ("男".equals(stringValue)) {
            return 0;
        } else if ("女".equals(stringValue)) {
            return 1;
        } else {
            return null;
        }
    }
}

4.把文件中的数据解析出来放入list中getDataImport

java 复制代码
/**
     * 把文件中的数据解析出来放入list中
     * @param file
     * @return
     */
    @Override
    public List<UserVO> getDataImport(MultipartFile file) {
        Optional.ofNullable(file).orElseThrow(() -> new BizException("文件不能为空"));
        InputStream is = null;
        List<UserVO> userVOS = new ArrayList<>();
        try {
            //获取输入流
            is = file.getInputStream();
            /**
             *  调用方法EasyExcel.read():read方法指定文件名名称、使用哪个实体类解析、使用哪个监听器类处
             *  sheet方法指定读取哪个sheet的数据
             *  doRead() 方法发起最终的读取操作
             *  其中使用内部类的方式直接创建监听器
             */

            EasyExcel.read(is, UserVO.class, new ReadListener<UserVO>() {
                @Override
                public void invoke(UserVO user, AnalysisContext context) {
                    //把解析到的每一行数据都存入list中
                    userVOS.add(user);
                }

                @Override
                public void doAfterAllAnalysed(AnalysisContext context) {

                }
            }).charset(StandardCharsets.UTF_8).excelType(ExcelTypeEnum.CSV).sheet().doRead();

        } catch (Exception e) {
            e.printStackTrace();
            String errorMsg = null;
            if (e instanceof ExcelDataConvertException) {
                ExcelDataConvertException excelDataConvertException = (ExcelDataConvertException) e;
                String cellMsg = "";
                CellData<?> cellData = excelDataConvertException.getCellData();
                //这里有一个celldatatype的枚举值,用来判断CellData的数据类型
                CellDataTypeEnum type = cellData.getType();
                if (type.equals(CellDataTypeEnum.NUMBER)) {
                    cellMsg = cellData.getNumberValue().toString();
                } else if (type.equals(CellDataTypeEnum.STRING)) {
                    cellMsg = cellData.getStringValue();
                } else if (type.equals(CellDataTypeEnum.BOOLEAN)) {
                    cellMsg = cellData.getBooleanValue().toString();
                }
                errorMsg = String.format("excel表格:第%s行,第%s列,数据值为:%s,该数据值不符合要求,请检验后重新导入!请检查其他的记录是否有同类型的错误!", excelDataConvertException.getRowIndex() + 1, excelDataConvertException.getColumnIndex() + 1, cellMsg);
                log.error(errorMsg);
            }
            throw new BizException(errorMsg);
        } finally {
            IoUtil.close(is);
        }
        return userVOS;

    }

总结

只要excel(csv)中的表头和实体类表头上的注解说明一致,则可以方便快捷的读取文件中的数据

相关推荐
IT毕设实战小研6 小时前
基于Spring Boot 4s店车辆管理系统 租车管理系统 停车位管理系统 智慧车辆管理系统
java·开发语言·spring boot·后端·spring·毕业设计·课程设计
一只爱撸猫的程序猿7 小时前
使用Spring AI配合MCP(Model Context Protocol)构建一个"智能代码审查助手"
spring boot·aigc·ai编程
甄超锋7 小时前
Java ArrayList的介绍及用法
java·windows·spring boot·python·spring·spring cloud·tomcat
武昌库里写JAVA9 小时前
JAVA面试汇总(四)JVM(一)
java·vue.js·spring boot·sql·学习
阿巴~阿巴~10 小时前
深入解析C++ STL链表(List)模拟实现
开发语言·c++·链表·stl·list
Pitayafruit10 小时前
Spring AI 进阶之路03:集成RAG构建高效知识库
spring boot·后端·llm
zru_960210 小时前
Spring Boot 单元测试:@SpyBean 使用教程
spring boot·单元测试·log4j
甄超锋11 小时前
Java Maven更换国内源
java·开发语言·spring boot·spring·spring cloud·tomcat·maven
还是鼠鼠12 小时前
tlias智能学习辅助系统--Maven 高级-私服介绍与资源上传下载
java·spring boot·后端·spring·maven
舒一笑16 小时前
Started TttttApplication in 0.257 seconds (没有 Web 依赖导致 JVM 正常退出)
jvm·spring boot·后端