Excel导出指定格式

news2024/11/17 7:35:41

期望

期望

实现

@Slf4j
@RequestMapping(value = "/data")
@RestController
public class DataStatController {

    @GetMapping(value = "/export", produces = MediaType.APPLICATION_OCTET_STREAM_VALUE)
    public void export(HttpServletResponse response) {
        final String filename = "easyexcel-tpl-export-demo.xlsx";

        // 获取要导出的数据列表/这里构造的假的,真实场景中应从数据库查询并转换为ExcelVO
        List<DoctorReportForm> excelVOS = getDoctorReportFormList();

        // 获取列表标题列表
        List<String> propNameCns = ExcelUtil.getPropNameCns(DoctorReportForm.class);
        List<String> propNameEns = ExcelUtil.getPropNameEns(DoctorReportForm.class);

        try (ServletOutputStream out = response.getOutputStream();
             SXSSFWorkbook wb = new SXSSFWorkbook()) {
            SXSSFSheet sheet = wb.createSheet();
            SXSSFRow row = sheet.createRow(0);
            for (int i = 0; i < propNameCns.size(); i++) {
                row.createCell(i).setCellValue(propNameCns.get(i));
            }

            for (DoctorReportForm excelVO : excelVOS) {
                Map<String, Object> excelVOMap = BeanMapUtil.beanToMap(excelVO);
                List<PhysiotherapyDetail> details = excelVO.getPhysiotherapyDetails();
                int size = (!CollectionUtils.isEmpty(details) || details.size() > 1) ? details.size() : 1;
                int beginRowNum = sheet.getLastRowNum() + 1;
                row = sheet.createRow(beginRowNum);
                row.createCell(0).setCellValue(excelVO.getProvinceName());
                int endRowNum = beginRowNum + size - 1;
                // 定义合并范围,参数依次是起始行号、结束行号、起始列号、结束列号
                for (int i = 0; i <= 6; i++) {
                    row.createCell(i).setCellValue((String) excelVOMap.get(propNameEns.get(i)));
                    CellRangeAddress rangeAddress = new CellRangeAddress(beginRowNum, endRowNum, i, i);
                    if (size > 1) sheet.addMergedRegion(rangeAddress);
                }

                // list的特殊处理
                int subRowNum = beginRowNum;
                for (PhysiotherapyDetail detail : details) {
                    List<String> nameEns = ExcelUtil.getPropNameEns(PhysiotherapyDetail.class);
                    Map<String, Object> detailMap = BeanMapUtil.beanToMap(detail);
                    if (subRowNum > beginRowNum) {
                        row = sheet.createRow(sheet.getLastRowNum() + 1);
                    }
                    for (int i = 7; i <= 10; i++) {
                        row.createCell(i).setCellValue((String) detailMap.get(nameEns.get(i - 7)));
                    }
                    subRowNum++;
                }
            }

            // 用流的形式传输
            response.setHeader(HttpHeaders.CONTENT_TYPE, "application/octet-stream");
            // 防止中文乱码
            try {
                response.setHeader(HttpHeaders.CONTENT_DISPOSITION, "attachment;filename=" + URLEncoder.encode(filename, StandardCharsets.UTF_8.name()));
            } catch (UnsupportedEncodingException e) {
                throw new EasyExcelException(EasyExcelExtExceptionTypes.ENCODE_NOT_SUPPORTED);
            }
            wb.write(out);
        } catch (IOException e) {
            throw new EasyExcelException(EasyExcelExtExceptionTypes.EXPORT_FAILED);
        }
    }

    // 构造虚假数据
    private static List<DoctorReportForm> getDoctorReportFormList() {
        List<DoctorReportForm> excelVOS = new ArrayList<>();
        excelVOS.add(DoctorReportForm.builder()
                .provinceName("辽宁省").cityName("沈阳市").belongArea("皇家分院").lecturer("李蛋")
                .avgPreDiagnosisRate("0.00%").avgOutputRate("0.00%").whichRound("1")
                .physiotherapyDetails(Arrays.asList(
                        PhysiotherapyDetail.builder()
                                .belongDeptName("皇家二科").deptJoinRoundCnt("1")
                                .preDiagnosisRate("0.00%").outputRate("0.00%").build(),
                        PhysiotherapyDetail.builder()
                                .belongDeptName("皇家一科").deptJoinRoundCnt("1")
                                .preDiagnosisRate("36.42%").outputRate("0.00%").build()))
                .build()
        );
        excelVOS.add(DoctorReportForm.builder()
                .provinceName("河南省").cityName("洛阳市").belongArea("皇家分院").lecturer("梦之花")
                .avgPreDiagnosisRate("0.30%").avgOutputRate("0.21%").whichRound("1")
                .physiotherapyDetails(Arrays.asList(
                        PhysiotherapyDetail.builder()
                                .belongDeptName("皇家八科").deptJoinRoundCnt("1")
                                .preDiagnosisRate("3.20%").outputRate("4.10%").build(),
                        PhysiotherapyDetail.builder()
                                .belongDeptName("皇家九科").deptJoinRoundCnt("1")
                                .preDiagnosisRate("2.50%").outputRate("3.30%").build(),
                        PhysiotherapyDetail.builder()
                                .belongDeptName("皇家十科").deptJoinRoundCnt("1")
                                .preDiagnosisRate("37.42%").outputRate("54.26%").build()))
                .build()
        );
        return excelVOS;
    }
}

源代码

easyexcel-tpl-export-demo

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

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

相关文章

docker 存储管理

文章目录 docker 存储管理容器存储方案docker 容器存储解决方案 docker 存储驱动基本概述存储驱动的选择原则主流的 docker 存储驱动docker 版本支持的存储驱动 overlay2 存储驱动OverlayFSoverlay2 存储驱动要求配置 docker 使用 overlay2 驱动 overlay2 存储驱动的工作机制Ov…

mybatis-plus常用使用方法

** mybaits-plus常用使用方法 ** 常用三层分别继承方法 1.1mapper层&#xff08;接口定义层&#xff09;可以用BaseMapper<> 例如&#xff1a; 1.2.里面常用的封装方法有 1.3常用方法介绍 【添加数据&#xff1a;&#xff08;增&#xff09;】int insert(T entity);…

Neo4j 国内镜像下载与安装

Neo4j 5.x 简体中文版指南 社区版&#xff1a;https://neo4j.com/download-center/#community 链接地址&#xff08;Linux版&#xff09;&#xff1a;https://neo4j.com/artifact.php?nameneo4j-community-3.5.13-unix.tar.gz 链接地址&#xff08;Windows&#xff09;&#x…

uml时序图刻画多个线程的活动

使用box关键字圈入不同线程内的组件 使用loop关键字客刻画线程的定时活动 示例

新建一个基于标准库的工程(STM32)

目录 1.新建存放工程的文件夹 2.打开KEIL5软件 3.新建一个本次工程的文件夹 4.添加工程的必要文件 4.1打开STM32的启动文件 ​编辑 4.2&#xff1a; 4.3添加内核寄存器文件 ​编辑 5.回到keil5软件&#xff0c;将刚才复制的那些文件添加到工程中 5.1添加一个启动文件&am…

vue3+naiveUI二次封装的v-model cascader联级选择框

组件 v-model 源码 <template><div class"clw-cascader pt-3"><n-cascaderref"cascader":value"value":title"title"filterableclearable:check-strategy"checkStrategy":label-field"labelField"…

在 ASP.NET Core Web API 中使用操作筛选器统一处理通用操作

前言&#xff1a;什么是操作筛选器 操作筛选器是 ASP.NET Core Web API 中的一种过滤器&#xff0c;用于在执行控制器操作&#xff08;Action&#xff09;之前或之后执行一些代码&#xff0c;完成特定的功能&#xff0c;比如执行日志记录、身份验证、授权、异常处理等通用的处…

2、鼠标事件、键盘事件、浏览器事件、监听事件、冒泡事件、默认事件、属性操作

一、鼠标事件 1、单击事件&#xff1a;onclick <body><header id"head">我是头部标签</header> </body> <script> var head document.getElementById("head")head.onclick function () {console.log("我是鼠标单击…

Elasticsearch使用经验和云上竞品对比

Elasticsearch使用经验和云上竞品对比 - 知乎 过去三十年&#xff0c;我们从企业应用开始&#xff0c;经历了 PC 互联网、移动互联网的爆发式发展&#xff0c;到如今的产业互联网。在这些不同时代&#xff0c;一直变化的是应用形态&#xff0c;不变的是核心数据的价值。 对于核…

kafka summary

最近整体梳理之前用到的一些东西&#xff0c;回顾Kafka的时候好多东西都忘记了&#xff0c;把一些自己记的比较模糊并且感觉有用的东西整理一遍并且记忆一遍&#xff0c;仅用于记录以备后续回顾 Kafka的哪些场景中使用了零拷贝 生产者发送消息&#xff1a;在 Kafka 生产者发送…

五、Kotlin 函数进阶

1. 高阶函数 1.1 什么是高阶函数 以下 2 点至少满足其一的函数称为高阶函数&#xff1a; 形参列表中包含函数类型的参数 //参数 paramN 可以是&#xff1a;函数引用、函数类型变量、或 Lambda 表达式。 fun funName(param1: Type1, param2: Type2, ... , paramN: (p1: T1, p2…

7.【SpringBoot3】项目部署、属性配置、多环境开发

1. SpringBoot 项目部署 项目完成后&#xff0c;需要部署到服务器上。 SpringBoot 项目需要经过编译打包生成一个 jar 包&#xff08;借助打包插件 spring-boot-maven-plugin&#xff09;&#xff0c;再将该 jar 包发送或拷贝到服务器上&#xff0c;然后就可以通过执行 java …

【AndroidStudio】2022.3Giraffe连接超时,更换下载源,使用本地gradle,版本对应问题

记录了使用AndroidStudio2022.3 Giraffe版本在搭建环境时遇到的问题&#xff0c;包括连接超时&#xff0c;gradle无法读取等。 如果只看如何正确的配置&#xff0c;直接跳转第3节 配置汇总 1 连接超时 项目一开始会自动下载gardle文件来加载项目 1.1 Connect timed out 基…

【NodeJS JS】动态加载字体的各方式及注意事项;

首先加载字体这个需求基本只存在于非系统字体&#xff0c;系统已有字体不需要加载即可直接使用&#xff1b; 方案1&#xff1a;创建 style 标签&#xff0c;写入 font-face{font-family: xxx;src: url(xxx)} 等相关字体样式&#xff1b;将style标签添加到body里&#xff1b;方…

网站将http升级到https大概要多少费用

随着网络安全意识的不断提升&#xff0c;越来越多的网站正从传统的HTTP协议转向更安全的HTTPS协议。这一转变的核心在于部署SSL&#xff08;Secure Sockets Layer&#xff09;或TLS&#xff08;Transport Layer Security&#xff09;证书&#xff0c;以实现数据加密传输&#x…

数据结构(顺序表)

文章目录 一、线性表1、线性表1.1、线性表的定义1.2、线性表的操作 2、顺序表2.1、顺序表的实现--静态分配2.2、顺序表的实现--动态分配2.2、顺序表的特点 3、顺序表的基本操作3.1、插入操作3.2、删除操作3.3、查找操作3.2、按位查找3.2、按值查找 一、线性表 1、线性表 1.1、…

自动驾驶的决策层逻辑

作者 / 阿宝 编辑 / 阿宝 出品 / 阿宝1990 自动驾驶意味着决策责任方的转移 我国2020至2025年将会是向高级自动驾驶跨越的关键5年。自动驾驶等级提高意味着对驾驶员参与度的需求降低&#xff0c;以L3级别为界&#xff0c;低级别自动驾驶环境监测主体和决策责任方仍保留于驾驶…

大数据数据流分析和处理的工具pig,从入门到精通!

介绍&#xff1a;Pig是一种数据流语言和运行环境&#xff0c;用于处理和分析大数据。 Pig由两个主要部分构成&#xff1a; Pig Latin语言&#xff1a;这是一种用于描述数据流的高级语言&#xff0c;它允许用户以较为简洁的方式编写数据处理和转换任务。 Pig执行环境&#xff1a…

JVM工作原理与实战(二十八):内存溢出和内存泄漏

专栏导航 JVM工作原理与实战 RabbitMQ入门指南 从零开始了解大数据 目录 专栏导航 前言 一、内存溢出与内存泄漏 1.内存溢出与内存泄漏介绍 2.内存泄漏的常见场景 3.解决内存溢出的步骤 总结 前言 JVM作为Java程序的运行环境&#xff0c;其负责解释和执行字节码&#x…

<蓝桥杯软件赛>零基础备赛20周--第18周--动态规划初步

报名明年4月蓝桥杯软件赛的同学们&#xff0c;如果你是大一零基础&#xff0c;目前懵懂中&#xff0c;不知该怎么办&#xff0c;可以看看本博客系列&#xff1a;备赛20周合集 20周的完整安排请点击&#xff1a;20周计划 每周发1个博客&#xff0c;共20周。 在QQ群上交流答疑&am…