大批量到处excel,防止内存溢出

2024-05-13 13:32

本文主要是介绍大批量到处excel,防止内存溢出,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

最近在做项目功能时 ,发现有20万以上的数据。要求导出时直接导出成压缩包。原来的逻辑是使用poi导出到excel,他是操作对象集合然后将结果写到excel中。

使用poi等导出时,没有考虑数据量的问题,大数据量无法满足,有个几千行jvm就哭了。更别提几万行几百万行数据了。

经过一天的研究发现一种不会消耗过多内存的方法:

导出成csv格式

大数据量的导出成csv格式分为以下几步:

1.首先引入需要的jar包 一下是我maven的配置方式

1

2

3

4

5

6

7

8

9

10

<dependency>

        <groupId>org.mvel</groupId>

        <artifactId>mvel2</artifactId>

        <version>2.2.8.Final</version>

    </dependency>

    <dependency>

        <groupId>net.sourceforge.javacsv</groupId>

        <artifactId>javacsv</artifactId>

        <version>2.0</version>

    </dependency>

 2.以下是具体的执行代码,我是用的是jdbcTemplate

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

36

public class DownloadVehicleRepair extends AbstractJob {

 

    @Autowired

    private JdbcTemplate jdbcTemplate;

 

    @Override

    protected void executeBusiness(Long aLong) {

        System.out.println("开始执行!!!!!!!!!!");

        final String fileName = "车辆维修清单.csv";//压缩包里面的文件

        final String[] header = {"序号""第三方机构代码""机构名称""分公司""合作机构""单位类别""主品牌""品牌名称",

                "被投诉""涉及欺诈""黑名单""审核状态""维护时间""维护人员代码"};

        final String sql = "您需要执行sql”;

 

        jdbcTemplate.execute(new PreparedStatementCreator() {

            @Override

            public PreparedStatement createPreparedStatement(Connection connection) throws SQLException {

                PreparedStatement pstmt = connection.prepareStatement(sql);

                return pstmt;

            }

        }, new PreparedStatementCallback<Integer>() {

            @Override

            public Integer doInPreparedStatement(PreparedStatement preparedStatement) throws SQLException, DataAccessException {

                ResultSet rs = preparedStatement.executeQuery();

                try {

                    CsvUtil.writeCsv(RuntimeEnvironmentUtil.getValue(SysConstent.code,SysConstent.path) + "\\VehicleRepairDetail.zip",

                            fileName, header, rs);//RuntimeEnvironmentUtil.getValue()是为了获取你导出到服务器的路径

                catch (Exception e) {

                    e.printStackTrace();

                }

                return 0;

            }

        });

        System.out.println("导出完成!!!!!!!!!!!");

 

    }

}

 3.以下是帮助类

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

36

37

38

39

40

41

42

43

44

45

46

47

48

49

50

51

52

53

54

55

56

57

58

59

60

61

62

63

64

65

66

67

68

69

70

71

72

73

74

75

76

77

78

79

80

81

82

public class CsvUtil {

    // 编码类型

    public static final Charset CHARSET = Charset.forName("GBK");

 

    // 分隔符

    public static final char DELIMITER = ',';

 

    // 文件后缀

    public static final String SUFFIX = ".csv";

 

 

    public static void writeCsv(OutputStream out, String[] header, ResultSet rs)

            throws IOException, SQLException {

        CsvWriter writer = null;

        try {

            writer = new CsvWriter(out, CsvUtil.DELIMITER, CsvUtil.CHARSET);

            writeCsv(writer, header, rs);

        finally {

            if (writer != null)

                writer.close();

        }

    }

 

    public static void writeCsv(CsvWriter writer, String[] header, ResultSet rs)

            throws IOException, SQLException {

        if (header != null)

            writer.writeRecord(header);

        ResultSetMetaData md = rs.getMetaData();

        int columnCount = md.getColumnCount();

        while (rs.next()) {

            for (int i = 1; i <= columnCount; i++)

                writer.write(rs.getString(i));

            writer.endRecord();

        }

    }

 

    public static void writeCsv(File file, String[] header, ResultSet rs)

            throws IOException, SQLException {

        BufferedOutputStream out = null;

        FileOutputStream fileOutputStream = null;

        try {

            fileOutputStream = new FileOutputStream(file);

            out = new BufferedOutputStream(fileOutputStream);

            writeCsv(out, header, rs);

        finally {

            if (out != null) {

                out.flush();

                out.close();

            }

            if (fileOutputStream != null) {

                fileOutputStream.close();

            }

        }

    }

 

    public static void writeCsv(String csvFilePath, String[] header,

                                ResultSet rs) throws IOException, SQLException {

        writeCsv(new File(csvFilePath), header, rs);

    }

 

    public static void writeCsv(String zipFilePath, String csvName, String[] header, ResultSet rs)

            throws IOException, SQLException {

        FileOutputStream fos = null;

        BufferedOutputStream bos = null;

        ZipOutputStream zos = null;

        try {

            fos = new FileOutputStream(zipFilePath);

            bos = new BufferedOutputStream(fos);

            zos = new ZipOutputStream(bos);

            zos.putNextEntry(new ZipEntry(csvName));

            writeCsv(zos, header, rs);

        finally {

            StreamUtil.flush(zos);

            StreamUtil.close(zos);

            //StreamUtil.flush(bos);

            StreamUtil.close(bos);

            //StreamUtil.flush(fos);

            StreamUtil.close(fos);

        }

    }

 

}

 

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

public class StreamUtil {

    public static void flush(Flushable flushable) {

        if (flushable != null) {

            try {

                flushable.flush();

            catch (IOException e) {

                e.printStackTrace();

            }

        }

    }

    public static void close(Closeable closeable){

        if(closeable!=null){

            try {

                closeable.close();

            catch (IOException e) {

                e.printStackTrace();

            }

        }

    }

}

 4.下面是下载时的action

1

2

3

4

5

6

7

8

9

10

@RequestMapping(value = "/downloadVehicleRepair", method = RequestMethod.POST)

   public ResponseEntity<byte[]> download() throws IOException {

       String path = RuntimeEnvironmentUtil.getValue(SysConstent.code,SysConstent.path)+"\\VehicleRepairDetail.zip";

       File file = new File(path);

       HttpHeaders headers = new HttpHeaders();

       String fileName = new String("车辆维修清单.zip".getBytes("UTF-8"), "iso-8859-1");//为了解决中文名称乱码问题

       headers.setContentDispositionFormData("attachment", fileName);

       headers.setContentType(MediaType.APPLICATION_OCTET_STREAM);

       return new ResponseEntity<byte[]>(FileUtils.readFileToByteArray(file), headers, HttpStatus.OK);

   }

 总结:以上只是关键代码。使用时只需要稍加改变就可以运行。

这篇关于大批量到处excel,防止内存溢出的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/985841

相关文章

使用Java将各种数据写入Excel表格的操作示例

《使用Java将各种数据写入Excel表格的操作示例》在数据处理与管理领域,Excel凭借其强大的功能和广泛的应用,成为了数据存储与展示的重要工具,在Java开发过程中,常常需要将不同类型的数据,本文... 目录前言安装免费Java库1. 写入文本、或数值到 Excel单元格2. 写入数组到 Excel表格

利用Python打造一个Excel记账模板

《利用Python打造一个Excel记账模板》这篇文章主要为大家详细介绍了如何使用Python打造一个超实用的Excel记账模板,可以帮助大家高效管理财务,迈向财富自由之路,感兴趣的小伙伴快跟随小编一... 目录设置预算百分比超支标红预警记账模板功能介绍基础记账预算管理可视化分析摸鱼时间理财法碎片时间利用财

利用python实现对excel文件进行加密

《利用python实现对excel文件进行加密》由于文件内容的私密性,需要对Excel文件进行加密,保护文件以免给第三方看到,本文将以Python语言为例,和大家讲讲如何对Excel文件进行加密,感兴... 目录前言方法一:使用pywin32库(仅限Windows)方法二:使用msoffcrypto-too

Spring Boot中JSON数值溢出问题从报错到优雅解决办法

《SpringBoot中JSON数值溢出问题从报错到优雅解决办法》:本文主要介绍SpringBoot中JSON数值溢出问题从报错到优雅的解决办法,通过修改字段类型为Long、添加全局异常处理和... 目录一、问题背景:为什么我的接口突然报错了?二、为什么会发生这个错误?1. Java 数据类型的“容量”限制

如何使用 Python 读取 Excel 数据

《如何使用Python读取Excel数据》:本文主要介绍使用Python读取Excel数据的详细教程,通过pandas和openpyxl,你可以轻松读取Excel文件,并进行各种数据处理操... 目录使用 python 读取 Excel 数据的详细教程1. 安装必要的依赖2. 读取 Excel 文件3. 读

C#实现将Excel表格转换为图片(JPG/ PNG)

《C#实现将Excel表格转换为图片(JPG/PNG)》Excel表格可能会因为不同设备或字体缺失等问题,导致格式错乱或数据显示异常,转换为图片后,能确保数据的排版等保持一致,下面我们看看如何使用C... 目录通过C# 转换Excel工作表到图片通过C# 转换指定单元格区域到图片知识扩展C# 将 Excel

在Spring Boot中浅尝内存泄漏的实战记录

《在SpringBoot中浅尝内存泄漏的实战记录》本文给大家分享在SpringBoot中浅尝内存泄漏的实战记录,结合实例代码给大家介绍的非常详细,感兴趣的朋友一起看看吧... 目录使用静态集合持有对象引用,阻止GC回收关键点:可执行代码:验证:1,运行程序(启动时添加JVM参数限制堆大小):2,访问 htt

使用Python将JSON,XML和YAML数据写入Excel文件

《使用Python将JSON,XML和YAML数据写入Excel文件》JSON、XML和YAML作为主流结构化数据格式,因其层次化表达能力和跨平台兼容性,已成为系统间数据交换的通用载体,本文将介绍如何... 目录如何使用python写入数据到Excel工作表用Python导入jsON数据到Excel工作表用

Python如何使用__slots__实现节省内存和性能优化

《Python如何使用__slots__实现节省内存和性能优化》你有想过,一个小小的__slots__能让你的Python类内存消耗直接减半吗,没错,今天咱们要聊的就是这个让人眼前一亮的技巧,感兴趣的... 目录背景:内存吃得满满的类__slots__:你的内存管理小助手举个大概的例子:看看效果如何?1.

java中使用POI生成Excel并导出过程

《java中使用POI生成Excel并导出过程》:本文主要介绍java中使用POI生成Excel并导出过程,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教... 目录需求说明及实现方式需求完成通用代码版本1版本2结果展示type参数为atype参数为b总结注:本文章中代码均为