Easyexcel读取单/多sheet页

Easyexcel读取单/多sheet页

此文档会说明单个和多个的sheet页的读取方法,包括本人在使用过程中的踩坑点。

依赖不会的自行百度导入,话不多说,直接上干货。以下示例基于2.x,新版本基本类似

1、创建实体

实体是用来接收对应列的数据的,官方文档中说明了可以用列号和列名进行指定

@Data
public class DemoExcelVO {@ExcelIgnoreprivate String idNo;@ExcelProperty(value = "工时类型")private String workType;@ExcelProperty(index = 3)private String deliveryPhase;@ExcelIgnoreprivate Integer orderBy;@ExcelIgnoreprivate String workTypeEmptyColumn;@ExcelIgnoreprivate String column;
}

创建实体如上所示,workType字段就是按照列名进行读取,deliveryPhase则是按照列号进行读取,更推荐使用列名指定,避免列的顺序出现变动影响读取数据的准确性。

需要特别注意,文档中多余的字段需要使用@ExcelIgnore进行标注,或者干脆不要写在这个实体内,接受完数据后自己去转对应的实体VO或者DTO。

读取excel文件

读取的方式有两种,

1、使用匿名内部类

如果是单个sheet页可以使用匿名内部类,这样就可以不用额外去写一个DemoDataListener。示例如下:

EasyExcel.read(inputStream, DemoExcelVO.class, new AnalysisEventListener<DemoExcelVO>() {// 存放列数据List<DemoExcelVO> dataList = new ArrayList<>();/*** 这里会一行行的返回头** @param headMap* @param context*/@Overridepublic void invokeHead(Map<Integer, CellData> headMap, AnalysisContext context) {// 这里是接收表头的,默认为第一行为表头,多行表头建议使用下面的第二种方法读excelMap<Integer, String> map = ConverterUtils.convertToStringMap(headMap, context);List<String> headNames = new ArrayList<>(map.values());// 这里可以做一些表头的校验之类的逻辑/** 逻辑处理* ....*/}/*** 这个每一条数据解析都会来调用** @param data* @param context*/@Overridepublic void invoke(DemoExcelVO data, AnalysisContext context) {// 它会按照你提供的实体对象一行一行的对应赋值,每读取一行就会进入一次这个方法,所以这个方法可以处理单行的数据逻辑,最后添加到list中/** 逻辑处理* ....*/// 添加到list中dataList.add(data);}/*** 将解析的数据缓存入redis,过期时间为第二天结束** @param context*/@Overridepublic void doAfterAllAnalysed(AnalysisContext context) {// 上面把每一行的数据读取完之后,就会进入到这个方法,一般是处理dataList的数据/** 逻辑处理* ....*/}
}).sheet().doRead();

2、写读的监听器

这里有讲究,因为有两种实现,可以实现ReadListener接口,也可以继承AnalysisEventListener,下面我们一起看看有什么不同。

1、实现ReadListener接口

public class DemoListener implements ReadListener {@Overridepublic void onException(Exception exception, AnalysisContext context) throws Exception {}@Overridepublic void invoke(Object data, AnalysisContext context) {}@Overridepublic void doAfterAllAnalysed(AnalysisContext context) {}@Overridepublic boolean hasNext(AnalysisContext context) {return false;}@Overridepublic void invokeHead(Map headMap, AnalysisContext context) {}
}

这里我就不一一对类进行说明了,可以基本和我上面的匿名内部类说明逻辑相似。

有坑!这个地方要注意,如果我们是直接实现的ReadListener然后快捷键按出来的具体实现方法,如下:

请添加图片描述

默认的话是会全选的,那么出来就是上面我给的代码那样子。问题就是出在**hasNext()**这个方法,这里我也没去深究,但是如果你默认不去更改,return false的话是无法读取到数据的。借用一下别人的说明:hasNext()这个方法是如果此扫描器的输入中有另一个标记,则返回 true。在等待要扫描的输入时,此方法可能阻塞。扫描器将不执行任何输入。所以循环会一直下去。

因此我们要记得把这个hasNext()调整为true,或者直接把这个方法干掉!

2、继承AnalysisEventListener

public class DemoListener extends AnalysisEventListener {@Overridepublic void invoke(Object data, AnalysisContext context) {}@Overridepublic void doAfterAllAnalysed(AnalysisContext context) {}
}

需要重写的方法只有两个,分别是针对每行数据的处理和对最后结果的处理,如果数据简单推荐用继承AnalysisEventListener去实现监听器,没啥坑。

下面是针对本次demo的具体实现:

Listener类:

public class DemoListener implements ReadListener {// 存放列数据@Getterprivate final List<DemoExcelVO> dataList = new ArrayList<>();/*** 这里会一行行的返回头** @param headMap* @param context*/@Overridepublic void invokeHead(Map<Integer, CellData> headMap, AnalysisContext context) {// 这里是接收表头的,默认为第一行为表头,多行表头建议使用下面的第二种方法读excelMap<Integer, String> map = ConverterUtils.convertToStringMap(headMap, context);List<String> headNames = new ArrayList<>(map.values());// 这里可以做一些表头的校验之类的逻辑/** 逻辑处理* ....*/}/*** 这个每一条数据解析都会来调用** @param data* @param context*/@Overridepublic void invoke(DemoExcelVO data, AnalysisContext context) {// 它会按照你提供的实体对象一行一行的对应赋值,每读取一行就会进入一次这个方法,所以这个方法可以处理单行的数据逻辑,最后添加到list中/** 逻辑处理* ....*/// 添加到list中dataList.add(data);}/*** 将解析的数据缓存入redis,过期时间为第二天结束** @param context*/@Overridepublic void doAfterAllAnalysed(AnalysisContext context) {// 上面把每一行的数据读取完之后,就会进入到这个方法,一般是处理dataList的数据/** 逻辑处理* ....*/}@Overridepublic void onException(Exception exception, AnalysisContext context) throws Exception {// 这里是异常的处理,可以选择抛出自定义的异常。}@Overridepublic boolean hasNext(AnalysisContext context) {return true;}
}

业务方法:

public void demoImport(MultipartFile file) {ExcelReader excelReader;try (InputStream inputStream = file.getInputStream()) {excelReader = EasyExcel.read(inputStream).build();}catch (IOException e) {throw new EdmpRuntimeException("文件流读取错误!");}if (excelReader == null) {throw new EdmpRuntimeException("文件流读取错误!");}// 读取Sheet页数据,如果是多个sheet页面需要多个Listener,比如readSheet1、readSheet2DemoListener demoListener = new DemoListener();ReadSheet readSheet = EasyExcel.readSheet("demo").head(DemoExcelVO.class).registerReadListener(demoListener).build();excelReader.read(readSheet);// 获取数据List<DemoExcelVO> dataList = demoListener.getDateList()/*处理业务*/
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/237195.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

【QT】QGraphicsView和QGraphicsItem坐标转换

坐标转换 QGraphicsItem和QGraphicsView之间的坐标转换需要通过QGraphicsScene进行转换 QGraphicsView::mapToScene() - 视图 -> 场景QGraphicsView::mapFromScene() - 场景 -> 视图QGraphicsItem::mapToScene() - 图元 -> 场景QGraphicsItem::mapFromScene() - 场景 …

C++ Qt开发:StringListModel字符串列表映射组件

Qt 是一个跨平台C图形界面开发库&#xff0c;利用Qt可以快速开发跨平台窗体应用程序&#xff0c;在Qt中我们可以通过拖拽的方式将不同组件放到指定的位置&#xff0c;实现图形化开发极大的方便了开发效率&#xff0c;本章将重点介绍QStringListModel字符串映射组件的常用方法及…

线程(四)

线程(一) ~ 线程(四)章节导图 导图https://naotu.baidu.com/file/07f437ff6bc3fa7939e171b00f133e17 线程安全 什么是线程安全&#xff1f; 业务中多线程同时访问一个对象或方法时我们不需要做额外的处理&#xff08;像单线程编程一样&#xff09;程序可以正常运行并能获取…

JS模块化规范之ES6及UMD

JS模块化规范之ES6及总结 前言ES6模块化概念基本使用ES6实现 UMD(Universal Module Definition)总结 前言 ESM在模块之间的依赖关系是高度确定的&#xff0c;与运行状态无关&#xff0c;编译工具只需要对ESM模块做静态分析&#xff0c;就可以从代码字面中推断出哪些模块值未曾被…

RocketMQ系统性学习-RocketMQ原理分析之Broker接收消息的处理流程

&#x1f308;&#x1f308;&#x1f308;&#x1f308;&#x1f308;&#x1f308;&#x1f308;&#x1f308; 【11来了】文章导读地址&#xff1a;点击查看文章导读&#xff01; &#x1f341;&#x1f341;&#x1f341;&#x1f341;&#x1f341;&#x1f341;&#x1f3…

【git学习笔记 01】打标签

文章目录 一、声明二、对标签的基本认知什么是标签&#xff1f;为什么要打标签&#xff1f;如何生成类似github中readme的图标 三、标签相关命令四、示例操作 一、声明 本帖持续更新中如有纰漏&#xff0c;望批评指正&#xff01;参考视频链接&#xff0c;非常感谢原作者&…

5 分钟内搭建一个免费问答机器人:Milvus + LangChain

搭建一个好用、便宜又准确的问答机器人需要多长时间&#xff1f; 答案是 5 分钟。只需借助开源的 RAG 技术栈、LangChain 以及好用的向量数据库 Milvus。必须要强调的是&#xff0c;该问答机器人的成本很低&#xff0c;因为我们在召回、评估和开发迭代的过程中不需要调用大语言…

Backtrader 文档学习-Data Feeds(下)

Backtrader 文档学习-Data Feeds&#xff08;下&#xff09; 1. Data Resampling 当数据仅在单个时间范围内可用&#xff0c;需要在不同的时间范围内进行分析时&#xff0c;就需要进行一些重采样。 “重采样”实际上应该称为“上采样”&#xff0c;因为它是从一个源时间区间到…

C++的泛型编程—模板

目录 一.什么是泛型编程&#xff1f; ​编辑 ​编辑 二.函数模板 函数模板的实例化 当不同类型形参传参时的处理 使用多个模板参数 三.模板参数的匹配原则 四.类模板 1.定义对象时要显式实例化 2.类模板不支持声明与定义分离 3.非类型模板参数 4.模板的特化 函数模板…

MySQL的安装及如何连接到Navicat和IntelliJ IDEA

MySQL的安装及如何连接到Navicat和IntelliJ IDEA 文章目录 MySQL的安装及如何连接到Navicat和IntelliJ IDEA1 MySQL安装1.1 下载1.2 安装(解压)1.3 配置1.3.1 添加环境变量1.3.2 新建配置文件1.3.3 初始化MySQL1.3.4 注册MySQL服务1.3.5 启动MySQL服务1.3.6 修改默认账户密码 1…

Windows中安装nvm进行Node版本控制

1.nvm介绍 nvm英文全程也叫node.js version management&#xff0c;是一个node.js的版本管理工具。nvm和npm都是node.js版本管理工具&#xff0c;但是为了解决node各种不同之间版本存在不兼容的问题&#xff0c;因此可以通过nvm安装和切换不同版本的node。 2.nvm下载 可在点…

6个免费设计资源站,设计师们赶紧收藏!

本期给大家分享5个免费的设计资源站&#xff0c;设计师必备的设计设计神奇&#xff0c;绝对能帮助你在工作中事半功倍&#xff0c;赶紧收藏吧~ 1、菜鸟图库 https://www.sucai999.com/?vNTYwNDUx 菜鸟图库是我推荐过很多次的网站&#xff0c;主要是站内素材多&#xff0c;像…

PHPStorm一站式配置

phpstorm安装好之后&#xff0c;先别急着编码。工欲善其事&#xff0c;必先利其器&#xff0c;配置好下面这些之后让编码事半功倍。 主题 Appearance & Behavior -> Appearance -> Theme 选中 [Light with Light Header] 亮色较为护眼 关闭更新 Appearance & …

C#学习笔记 - C#基础知识 - C#从入门到放弃 - C# 方法

C# 入门基础知识 - 方法 第8节 方法8.1 C# 函数/方法简介8.2 方法的声明及调用8.2.1 参数列表方法的声明及调用8.2.2 参数数组方法的声明及调用8.2.3、引用参数与值参数 8.3 静态方法和实例方法8.3.1 静态、实例方法的区别8.2.3 静态、实例方法的声明及其调用 8.4 虚方法8.4.1 …

Linux学习(3)——基本命令-文件

1、cat&#xff1a;查看文件内容--上下合并文件 注意&#xff1a;cat只能查看普通的文本文件 如果文件内容过多会显示不全 选项效果-n显示行号包括空行-b跳过空白行编号&#xff1b;注意&#xff0c;在一行打了空格不算空白行&#xff0c;enter键直接跳过这一行才算-s将所有连续…

【JAVA】CyclicBarrier源码解析以及示例

文章目录 前言CyclicBarrier源码解析以及示例主要成员变量核心方法 应用场景任务分解与合并应用示例 并行计算应用示例 游戏开发应用示例输出结果 数据加载应用示例 并发工具的协同应用示例 CyclicBarrier和CountDownLatch的区别循环性&#xff1a;计数器的变化&#xff1a;用途…

[c]用指针进行四个数排序

#include<stdio.h> void swap(int*p1,int*p2)//定义函数&#xff0c;实现两个数值交换 {int temp;temp*p1;*p1*p2;*p2temp; } void psort( int *pa, int *pb,int *pc,int *pd) {int i1;for(i1;i<3;i)//对四个数排序&#xff0c;至少3次循环&#xff0c;交换过后是升序…

DDPM推导笔记

各位佬看文章之前&#xff0c;可以先去看看这个视频&#xff0c;并给这位up主点赞投币&#xff0c;这位佬讲解的太好了&#xff1a;大白话AI 1.前置知识的学习 1.1 正态分布特性 ​ &#xff08;1&#xff09;正态分布的概率密度函数 f ( x ) 1 2 π σ e − ( x − μ ) …

Android13音频录制适配

Android13音频录制适配 前言&#xff1a; 之前写过一篇音频录制的文章&#xff0c;当时是在Android10以下的手机可以成功录制和播放&#xff0c;但是Android10及以上手机提示创建文件失败&#xff0c;最近做过Android13的适配&#xff0c;索性一起把之前的录音也适配了&#…

Python 时间日期处理库函数

标准库 datetime >>> import datetime >>> date datetime.date(2023, 12, 20) >>> print(date) 2023-12-20 >>> date datetime.datetime(2023, 12, 20) >>> print(date) 2023-12-20 00:00:00 >>> print(date.strfti…