0.简介

  1. Java领域解析、生成Excel比较有名的框架有Apache poi、jxl等。但他们都存在一个严重的问题就是非常的耗内存。如果你的系统并发量不大的话可能还行,但是一旦并发上来后一定会OOM或者JVM频繁的full gc
  2. EasyExcel是阿里巴巴开源的一个excel处理框架,以使用简单、节省内存著称。EasyExcel能大大减少占用内存的主要原因是在解析Excel时没有将文件数据一次性全部加载到内存中,而是从磁盘上一行行读取数据,逐个解析。
  3. EasyExcel采用一行一行的解析模式,并将一行的解析结果以观察者的模式通知处理(AnalysisEventListener)。

    1.Excel写操作

    1.引入依赖

    1. <dependencies>
    2. <!-- https://mvnrepository.com/artifact/com.alibaba/easyexcel -->
    3. <dependency>
    4. <groupId>com.alibaba</groupId>
    5. <artifactId>easyexcel</artifactId>
    6. <version>2.1.1</version>
    7. </dependency>
    8. </dependencies>

    2.创建实体类

    1. import com.alibaba.excel.annotation.ExcelProperty;
    2. //设置表头和添加的数据字段
    3. public class DemoData {
    4. //设置表头名称
    5. @ExcelProperty("学生编号")
    6. private int sno;
    7. //设置表头名称
    8. @ExcelProperty("学生姓名")
    9. private String sname;
    10. public int getSno() {
    11. return sno;
    12. }
    13. public void setSno(int sno) {
    14. this.sno = sno;
    15. }
    16. public String getSname() {
    17. return sname;
    18. }
    19. public void setSname(String sname) {
    20. this.sname = sname;
    21. }
    22. @Override
    23. public String toString() {
    24. return "DemoData{" +
    25. "sno=" + sno +
    26. ", sname='" + sname + '\'' +
    27. '}';
    28. }
    29. }

    3.实现写操作

    1.创建方法循环设置要添加到Excel的数据

    1. //循环设置要添加的数据,最终封装到list集合中
    2. private static List<DemoData> data() {
    3. List<DemoData> list = new ArrayList<DemoData>();
    4. for (int i = 0; i < 10; i++) {
    5. DemoData data = new DemoData();
    6. data.setSno(i);
    7. data.setSname("张三"+i);
    8. list.add(data);
    9. }
    10. return list;
    11. }

    2.实现最终的添加操作(写法一)

    1. public static void main(String[] args) throws Exception {
    2. // 写法1
    3. String fileName = "F:\\11.xlsx";
    4. // 这里 需要指定写用哪个class去写,然后写到第一个sheet,名字为模板 然后文件流会自动关闭
    5. // 如果这里想使用03 则 传入excelType参数即可
    6. EasyExcel.write(fileName, DemoData.class).sheet("写入方法一").doWrite(data());
    7. }

    3.实现最终的添加操作(写法二)

    1. public static void main(String[] args) throws Exception {
    2. // 写法2,方法二需要手动关闭流
    3. String fileName = "F:\\112.xlsx";
    4. // 这里 需要指定写用哪个class去写
    5. ExcelWriter excelWriter = EasyExcel.write(fileName, DemoData.class).build();
    6. WriteSheet writeSheet = EasyExcel.writerSheet("写入方法二").build();
    7. excelWriter.write(data(), writeSheet);
    8. /// 千万别忘记finish 会帮忙关闭流
    9. excelWriter.finish();
    10. }

    2.Excel读操作

    1.创建实体类

    1. import com.alibaba.excel.annotation.ExcelProperty;
    2. public class ReadData {
    3. //设置列对应的属性
    4. @ExcelProperty(index = 0)
    5. private int sid;
    6. //设置列对应的属性
    7. @ExcelProperty(index = 1)
    8. private String sname;
    9. public int getSid() {
    10. return sid;
    11. }
    12. public void setSid(int sid) {
    13. this.sid = sid;
    14. }
    15. public String getSname() {
    16. return sname;
    17. }
    18. public void setSname(String sname) {
    19. this.sname = sname;
    20. }
    21. @Override
    22. public String toString() {
    23. return "ReadData{" +
    24. "sid=" + sid +
    25. ", sname='" + sname + '\'' +
    26. '}';
    27. }
    28. }

    2.创建读取操作的监听器

    1. import com.alibaba.excel.context.AnalysisContext;
    2. import com.alibaba.excel.event.AnalysisEventListener;
    3. import com.alibaba.excel.exception.ExcelDataConvertException;
    4. import com.sun.scenario.effect.impl.sw.sse.SSEBlend_SRC_OUTPeer;
    5. import java.util.ArrayList;
    6. import java.util.List;
    7. import java.util.Map;
    8. //创建读取excel监听器
    9. public class ExcelListener extends AnalysisEventListener<ReadData> {
    10. //创建list集合封装最终的数据
    11. List<ReadData> list = new ArrayList<ReadData>();
    12. //一行一行去读取excle内容
    13. @Override
    14. public void invoke(ReadData user, AnalysisContext analysisContext) {
    15. System.out.println("***"+user);
    16. list.add(user);
    17. }
    18. //读取excel表头信息
    19. @Override
    20. public void invokeHeadMap(Map<Integer, String> headMap, AnalysisContext context) {
    21. System.out.println("表头信息:"+headMap);
    22. }
    23. //读取完成后执行
    24. @Override
    25. public void doAfterAllAnalysed(AnalysisContext analysisContext) {
    26. }
    27. }

    3. 调用实现最终的读取

    1. public static void main(String[] args) throws Exception {
    2. // 写法1:
    3. String fileName = "F:\\01.xlsx";
    4. // 这里 需要指定读用哪个class去读,然后读取第一个sheet 文件流会自动关闭
    5. EasyExcel.read(fileName, ReadData.class, new ExcelListener()).sheet().doRead();
    6. // 写法2:
    7. InputStream in = new BufferedInputStream(new FileInputStream("F:\\01.xlsx"));
    8. ExcelReader excelReader = EasyExcel.read(in, ReadData.class, new ExcelListener()).build();
    9. ReadSheet readSheet = EasyExcel.readSheet(0).build();
    10. excelReader.read(readSheet);
    11. // 这里千万别忘记关闭,读的时候会创建临时文件,到时磁盘会崩的
    12. excelReader.finish();
    13. }