Apache POI、EasyPoi、EasyExcel

news2025/1/12 6:08:54

 (一)Apache PoI 使用

 (二)EasyPoi使用

 (三)EasyExcel使用

官方文档:

写Excel | Easy Excel 官网

 写

使用注解在字段上进行标识

使用最简单的方法二即可

    /**
     * 最简单的写
     * <p>
     * 1. 创建excel对应的实体对象 参照{@link DemoData}
     * <p>
     * 2. 直接写即可
     */
    @Test
    public void simpleWrite() {
        // 注意 simpleWrite在数据量不大的情况下可以使用(5000以内,具体也要看实际情况),数据量大参照 重复多次写入

        // 写法1 JDK8+
        // since: 3.0.0-beta1
        String fileName = TestFileUtil.getPath() + "simpleWrite" + System.currentTimeMillis() + ".xlsx";
        // 这里 需要指定写用哪个class去写,然后写到第一个sheet,名字为模板 然后文件流会自动关闭
        // 如果这里想使用03 则 传入excelType参数即可
        EasyExcel.write(fileName, DemoData.class)
            .sheet("模板")
            .doWrite(() -> {
                // 分页查询数据
                return data();
            });

        // 写法2
        fileName = TestFileUtil.getPath() + "simpleWrite" + System.currentTimeMillis() + ".xlsx";
        // 这里 需要指定写用哪个class去写,然后写到第一个sheet,名字为模板 然后文件流会自动关闭
        // 如果这里想使用03 则 传入excelType参数即可
        EasyExcel.write(fileName, DemoData.class).sheet("模板").doWrite(data());

        // 写法3
        fileName = TestFileUtil.getPath() + "simpleWrite" + System.currentTimeMillis() + ".xlsx";
        // 这里 需要指定写用哪个class去写
        try (ExcelWriter excelWriter = EasyExcel.write(fileName, DemoData.class).build()) {
            WriteSheet writeSheet = EasyExcel.writerSheet("模板").build();
            excelWriter.write(data(), writeSheet);
        }
    }

最简单的读​

最简单的读的excel示例​

最简单的读的对象​

@Getter
@Setter
@EqualsAndHashCode
public class DemoData {
    private String string;
    private Date date;
    private Double doubleData;
}

读的时候涉及到一个监听器对象

自定义的监听器代码,

阿里巴巴要:因为监听器不受spring管理,所以你要想在监听器中操作数据库,必须按照人家要求使用构造方法传入

// 有个很重要的点 DemoDataListener 不能被spring管理,要每次读取excel都要new,然后里面用到spring可以构造方法传进去
//这个自定义监听器的功能是定义了一个100的缓冲区,没当list达到了100则写入数据库
@Slf4j
public class DemoDataListener implements ReadListener<DemoData> {

    /**
     * 每隔5条存储数据库,实际使用中可以100条,然后清理list ,方便内存回收
     */
    private static final int BATCH_COUNT = 100;
    /**
     * 缓存的数据
     */
    private List<DemoData> cachedDataList = ListUtils.newArrayListWithExpectedSize(BATCH_COUNT);
    /**
     * 假设这个是一个DAO,当然有业务逻辑这个也可以是一个service。当然如果不用存储这个对象没用。
     */
    private DemoDAO demoDAO;

    public DemoDataListener() {
        // 这里是demo,所以随便new一个。实际使用如果到了spring,请使用下面的有参构造函数
        demoDAO = new DemoDAO();
    }

    /**
     * 如果使用了spring,请使用这个构造方法。每次创建Listener的时候需要把spring管理的类传进来
     *
     * @param demoDAO
     */
    public DemoDataListener(DemoDAO demoDAO) {
        this.demoDAO = demoDAO;
    }

    /**
     * 这个每一条数据解析都会来调用
     *
     * @param data    one row value. Is is same as {@link AnalysisContext#readRowHolder()}
     * @param context
     */
    @Override
    public void invoke(DemoData data, AnalysisContext context) {
        log.info("解析到一条数据:{}", JSON.toJSONString(data));
        cachedDataList.add(data);
        // 达到BATCH_COUNT了,需要去存储一次数据库,防止数据几万条数据在内存,容易OOM
        if (cachedDataList.size() >= BATCH_COUNT) {
            saveData();
            // 存储完成清理 list
            cachedDataList = ListUtils.newArrayListWithExpectedSize(BATCH_COUNT);
        }
    }

    /**
     * 所有数据解析完成了 都会来调用,上面没达到100的,没有触发保存数据库
最后就执行这个方法,把遗留的存进去
     *
     * @param context
     */
    @Override
    public void doAfterAllAnalysed(AnalysisContext context) {
        // 这里也要保存数据,确保最后遗留的数据也存储到数据库
        saveData();
        log.info("所有数据解析完成!");
    }

    /**
     * 加上存储数据库
     */
    private void saveData() {
        log.info("{}条数据,开始存储数据库!", cachedDataList.size());
        demoDAO.save(cachedDataList);
        log.info("存储数据库成功!");
    }
}

 最简单的读

想省事不自定义监听器对象可以直接参考写法一

    /**
     * 最简单的读
     * <p>
     * 1. 创建excel对应的实体对象 参照{@link DemoData}
     * <p>
     * 2. 由于默认一行行的读取excel,所以需要创建excel一行一行的回调监听器,参照{@link DemoDataListener}
     * <p>
     * 3. 直接读即可
     */
    @Test
    public void simpleRead() {
        // 写法1:JDK8+ ,不用额外写一个DemoDataListener
        // since: 3.0.0-beta1
        String fileName = TestFileUtil.getPath() + "demo" + File.separator + "demo.xlsx";
        // 这里默认每次会读取100条数据 然后返回过来 直接调用使用数据就行
        // 具体需要返回多少行可以在`PageReadListener`的构造函数设置
        EasyExcel.read(fileName, DemoData.class, new PageReadListener<DemoData>(dataList -> {
            for (DemoData demoData : dataList) {
                log.info("读取到一条数据{}", JSON.toJSONString(demoData));
            }
        })).sheet().doRead();

        // 写法2:
        // 匿名内部类 不用额外写一个DemoDataListener
        fileName = TestFileUtil.getPath() + "demo" + File.separator + "demo.xlsx";
        // 这里 需要指定读用哪个class去读,然后读取第一个sheet 文件流会自动关闭
        EasyExcel.read(fileName, DemoData.class, new ReadListener<DemoData>() {
            /**
             * 单次缓存的数据量
             */
            public static final int BATCH_COUNT = 100;
            /**
             *临时存储
             */
            private List<DemoData> cachedDataList = ListUtils.newArrayListWithExpectedSize(BATCH_COUNT);

            @Override
            public void invoke(DemoData data, AnalysisContext context) {
                cachedDataList.add(data);
                if (cachedDataList.size() >= BATCH_COUNT) {
                    saveData();
                    // 存储完成清理 list
                    cachedDataList = ListUtils.newArrayListWithExpectedSize(BATCH_COUNT);
                }
            }

            @Override
            public void doAfterAllAnalysed(AnalysisContext context) {
                saveData();
            }

            /**
             * 加上存储数据库
             */
            private void saveData() {
                log.info("{}条数据,开始存储数据库!", cachedDataList.size());
                log.info("存储数据库成功!");
            }
        }).sheet().doRead();

        // 有个很重要的点 DemoDataListener 不能被spring管理,要每次读取excel都要new,然后里面用到spring可以构造方法传进去
        // 写法3:
        fileName = TestFileUtil.getPath() + "demo" + File.separator + "demo.xlsx";
        // 这里 需要指定读用哪个class去读,然后读取第一个sheet 文件流会自动关闭
        EasyExcel.read(fileName, DemoData.class, new DemoDataListener()).sheet().doRead();

        // 写法4
        fileName = TestFileUtil.getPath() + "demo" + File.separator + "demo.xlsx";
        // 一个文件一个reader
        try (ExcelReader excelReader = EasyExcel.read(fileName, DemoData.class, new DemoDataListener()).build()) {
            // 构建一个sheet 这里可以指定名字或者no
            ReadSheet readSheet = EasyExcel.readSheet(0).build();
            // 读取一个sheet
            excelReader.read(readSheet);
        }
    }

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

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

相关文章

入门PHP就来我这(纯干货)04

~~~~ 有胆量你就来跟着路老师卷起来&#xff01; -- 纯干货&#xff0c;技术知识分享 ~~~~ 路老师给大家分享PHP语言的知识了&#xff0c;旨在想让大家入门PHP&#xff0c;并深入了解PHP语言。 我们接着《想入门PHP就来我这&#xff08;纯干货&#xff09;03》继续往下学习&am…

忘记家里的wifi密码用iPhone苹果手机怎么找回?

忘记家里的wifi密码用iPhone苹果手机怎么找回&#xff1f; 1、打开iPhone苹果手机上的设置&#xff1b; 2、在iPhone苹果手机设置里找到并进入无线局域网&#xff1b; 3、选择要找回密码的wifi&#xff0c;且已连接&#xff0c;并点击后面的更多进入&#xff1b; 4、进入无线局…

Excel分组求和

目录 1 参考文章2 UNIQUE函数分组3 SUMIF函数分组求和 1 参考文章 1.整体思路&#xff1a;https://blog.csdn.net/Alice_loong/article/details/135580130 2.UNIQUE函数&#xff1a;https://mp.weixin.qq.com/s?__bizMzI3OTcwNDE3OQ&mid2247487044&idx1&sna28108…

浅谈Web性能测试(原创)

一、性能测试不是什么高技术的活&#xff1a; 说到性能测试&#xff0c;很多工作时间较短的新同事或者应届生就很害怕。 为什么害怕&#xff0c;因为感觉无从下手&#xff0c;不知道该做什么、怎么做、做到什么程度&#xff1f; 一听性能测试首先想到的是各种专业的性能测试…

Echarts-柱状图

1.案例1 1.1代码 option = {textStyle: {color: #fff // 标题文字颜色为白色},tooltip: {trigger: axis,axisPointer: {type: shadow,},},legend: {textStyle: {color: white}},grid: {top: 15%,left: 4%,right: 4%,bottom: 7%,containLabel: true},xAxis:{type: category,da…

分文件编译(简单学生系统)

定义学生基本信息 ①输出所有学生信息 ②删除某个学生后&#xff0c;输出所有学生信息 ③修改某个学生信息后&#xff0c;输出所有学生信息 ④查找某个学生的信息 main.c #include"k11*.h" int main(int argc, const char *argv[]) {struct student p[4]{{"…

ShareX:不仅仅是截图工具

名人说&#xff1a;莫道谗言如浪深&#xff0c;莫言迁客似沙沉。 ——刘禹锡《浪淘沙》 创作者&#xff1a;Code_流苏(CSDN)&#xff08;一个喜欢古诗词和编程的Coder&#x1f60a;&#xff09; 目录 一、软件介绍1、ShareX2、核心功能 二、下载安装1、下载2、安装 三、使用方法…

CentOS7.9下yum升级Apache HTTP Server2.4.6到2.4.60

CentOS7.9系统默认的Apache版本 在CentOS7.9上&#xff0c;如果使用yum安装Apache HTTP Server是最多到2.4.6版本的&#xff0c;这是因为el7下官方仓库的最高版本就是2.4.6&#xff0c;证据如下&#xff1a; $ yum info httpd ...... Installed Packages Name : httpd…

虚拟纪念展馆建设的重大意义:重新定义纪念活动的未来

一、什么是虚拟纪念展馆&#xff1f; 虚拟纪念展馆是一种利用3D、VR等技术在线展示历史事件、人物或文化遗产的数字化空间。这些展馆通过虚拟现实、增强现实和3D建模等技术手段&#xff0c;创建出身临其境的体验&#xff0c;使参观者可以在互联网上以互动方式探索和学习。 二、…

Golang | Leetcode Golang题解之第205题同构字符串

题目&#xff1a; 题解&#xff1a; func isIsomorphic(s, t string) bool {s2t : map[byte]byte{}t2s : map[byte]byte{}for i : range s {x, y : s[i], t[i]if s2t[x] > 0 && s2t[x] ! y || t2s[y] > 0 && t2s[y] ! x {return false}s2t[x] yt2s[y] …

nginx 只有图片等静态资源时 监听80端口 会404 NOT FOUND

解决方法 删除 /var/nginx/sites-enabled 原因&#xff1a;当nginx没有设置首页路径index时&#xff0c;sites-enabled目录中配置的优先级会高于nginx.conf 导致404 NOT FOUND sites-enabled文件中的default会将80端口索引至默认值&#xff1a;/var/www/html目录下&#xff…

Redis基础教程(八):redis集合(Set)

&#x1f49d;&#x1f49d;&#x1f49d;首先&#xff0c;欢迎各位来到我的博客&#xff0c;很高兴能够在这里和您见面&#xff01;希望您在这里不仅可以有所收获&#xff0c;同时也能感受到一份轻松欢乐的氛围&#xff0c;祝你生活愉快&#xff01; &#x1f49d;&#x1f49…

职场小白必备待办工具有哪些 适合新手的待办app

初入职场的小白们&#xff0c;常常会遇到各种挑战。从最初的迷茫&#xff0c;到对工作的逐步熟悉&#xff0c;每一步都需要时间和精力的投入。尤其是当面对繁多的工作任务时&#xff0c;如何快速有效地完成它们&#xff0c;成为了许多职场新人需要面对的问题。 在这个快节奏的…

数字集群手持终端是什么_鼎跃安全

在当今快速发展的科技时代&#xff0c;通信技术的进步为各行各业带来了巨大的变革。尤其是在公共安全、应急救援和交通运输等领域&#xff0c;通信的及时性和可靠性变得尤为重要。数字集群手持终端作为一种专用于数字集群通信系统的便携式设备&#xff0c;数字集群手持终端是一…

AI模特换装试衣软件定制服务公司

&#x1f31f; 最强AI模特换装试衣模型训练、定制服务公司出炉 —— 触站AI&#x1f680; &#x1f3a8; 在AI技术的浪潮中&#xff0c;触站AI以其专业和创新&#xff0c;成为企业AI图像领域的技术解决方案服务公司&#xff0c;为设计界带来了革命性的变化。 &#x1f6e0;️ …

PDF一键转PPT文件!这2个AI工具值得推荐,办公必备!

PDF转换为PPT文件&#xff0c;是职场上非常常见的需求&#xff0c;过去想要把PDF文件转换为PPT&#xff0c;得借助各种文件转换工具&#xff0c;但在如今AI技术主导的大背景下&#xff0c;我们在选用工具时有了更多的选择&#xff0c;最明显的就是基于AI技术打造的AI格式转换工…

恢复的实现技术-日志和数据转储

一、引言 在系统正常运行的情况下&#xff0c;事务处理的恢复机制应采取某些技术措施为恢复做好相应的准备&#xff0c;保证在系统发生故障后&#xff0c;能将数据库从一个不一致的错误状态恢复到一个一致性状态 恢复技术主要包括 生成一个数据库日志&#xff0c;来记录系统中…

机械行业常见问题及ERP解决办法

机械行业在全球经济一体化和技术进步背景下&#xff0c;面临着越来越多的挑战。为了在激烈的市场竞争中立于不败之地&#xff0c;企业需要找到合适的方法优化生产流程、降低成本、提升客户满意度。因此&#xff0c;有效地利用企业资源规划&#xff08;ERP&#xff09;解决方案变…

isidentifier()方法——判断字符串是否为合法的Python标识符或变量名

自学python如何成为大佬(目录):https://blog.csdn.net/weixin_67859959/article/details/139049996?spm1001.2014.3001.5501 语法参考 isidentifier()方法用于判断字符串是否是有效的Python标识符&#xff0c;还可以用来判断变量名是否合法。isidentifier()方法的语法格式如…

JAVA妇产科专科电子病历系统源码,前端框架:Vue,ElementUI

JAVA妇产科专科电子病历系统源码&#xff0c;前端框架&#xff1a;Vue&#xff0c;ElementUI孕产妇健康管理信息管理系统是一种将孕产妇健康管理信息进行集中管理和存储的系统。通过建立该系统&#xff0c;有助于提高孕产妇健康管理的效率和质量&#xff0c;减少医疗事故发生的…