重复工作自动化——excel导入方案

计算机与人相比,有什么优势?这个问题从计算机诞生之初就不断被回答:在重复性工作上,计算机有人类无法企及的计算速度和存储空间。因此,把重复性工作交给计算机,也就是常说的“可复用性”,是软件设计中的一个最基本的思想。

这里记录的这个小设计,就是把重复工作自动化处理的一个例子。

背景

在我们的系统中,经常有用户上传一个Excel文件、系统进行处理的需求。

Excel的处理框架,有Jxl和POI。我们的系统使用了POI框架,并封装了若干个Util工具类。但是,由于工具类的封装不到位,业务代码中仍然会有大量的解析Excel文件(并且还存留了很多只接受.xls文件、无法处理.xlsx文件的代码)、遍历sheet/row/cell、处理单元格和Java对象类型转换的重复代码。

因此,我设计实现了这个小小的工具。

思路

Excel导入的基本流程如下图所示。这个导入工具封装了校验、Excel转pojo这两个步骤,数据处理则作为扩展点留给了业务代码。

除基本功能外,这个框架还需要考虑性能问题。因此,方案中要为Excel转pojo和数据处理这两个操作预留异步的扩展点,以期提高处理效率。并且据我以前的测试,一个大小为1MB的Excel文件,放入JVM中之后要占用约2MB的内存空间。所以这个框架还应尽量节省(或者尽快释放)内存空间。

类图

文件导入框架的入口是FileImporrtor接口。主方法入参是一个标记接口,其中要求提供字节数组,作为待导入的文件数据。导入时如果还需要其它数据,可以在实现接口时自行扩展、提供。

这里将文件转化为字节数组,主要有两点考虑。一方面,这样做可以兼容不同格式、不同封装的文件。例如,无论是MultipartFile还是File、无论是txt还是doc文件,都可以在转成字节数组后纳入框架中来进行处理。另一方面,无论是File还是InputStream,都会占用句柄、连接等资源。管理这些资源并不是这个框架的职能——事实上,技术框架都无法确定业务资源应当何时关闭。因此,接口只接受字节数组形式的入参。

框架中实现了一个Excel的导入类FileImportor4Excel。这个类使用POI框架作为底层工具。其中处理其实很简单,就是使用POI解析出excel文件后,遍历其中的sheet/row/cell,将其中数据转换为Java封装类。

解析Excel的流程中,将数据转换为Java封装类是比较困难的一个点。因为Excel中的数据类型只有那么几种,定义为Cell中的几个int常量。但是Java类型却有千千万。如何把它们正确的转换为Java类型?框架中引入了CellValueTransfer和ExcelImportHelper这两个类。CellValueTransfer是一个接口,定义了将POI的Cell转换为Java类的方法,并提供了若干个基础实现类。而ExcelImportHelper则是一个辅助类,用于为当前的Cell和Java类找到合适的CellValueTransfer,并执行转换操作。

后来增加了FileImportor4ExcelParallel,引入了多线程来处理。其中使用的线程池是ForkJoinPool,因为Excel导入恰可以“分而治之”。不过引入多线程后,整个Excel中的数据就无法在同一个事务中进行处理了。

此外还增加了一个带回调函数的类FileImportor4ExcelCallback。因为原逻辑中,需要将Excel全部转换为List然后再做处理。加入Callback之后,则可以每转换一条数据就处理一条数据,并且可以在处理完成后迅速丢弃(设置为null)该数据,以尽快释放内存。

代码

https://github.com/winters1224/blogs/tree/master/code/src/main/java/net/loyintean/blog/fileimport

不过这里只有早期的部分代码,不包括后来的优化整理和功能扩展。

时间: 2024-10-23 14:38:07

重复工作自动化——excel导入方案的相关文章

excel导入导出优化

对于上一篇excel中出现的问题,在excel导入导出中都做了优化.还是eclipse+jdk1.8,但是这个项目是一个web项目,需要配合Tomcat服务器,并且使用了SSH框架, I/O操作过多 首先,对于I/O操作过多,那么就不像之前一样,一条一条的添加或者更新;而且凑齐一堆,也就是一个list集合,然后统一的批量保存. 使用SessionFactory获取当前的session,然后调用session的persist方法,保存实体.只是设置了一个批量的量值.每到30条数据,就将缓存同步到数

c#使用NPOI进行Excel导入导出,附源码,vs2010

目录 1. 介绍:描述第三方类库NPOI以及Excel结构 2. Excel导入:介绍C#如何调用NPOI进行Excel导入,包含:流程图.NOPI以及C#代码 3. Excel导出:介绍C#如何调用NPOI进行Excel导出,包含:流程图.NOPI以.C#代码以及代码分析 4. 源码下载:展示运行图及源码下载 1. 介绍 1.1 第三方类库:NPOI 说明:NPOI是POI项目的.NET 版本,可用于Excel.Word的读写操作. 优点:不用装Office环境. 下载地址:http://np

解析大型.NET ERP系统 设计通用Microsoft Excel导入功能

做企业管理软件很难避免与Microsoft Excel打交道,常常是软件做好了,客户要求说再做一个Excel导入功能.导入Excel数据的功能的难度不大,从Excel列数据栏位的取值,验证值,再导入到数据库表中.然而一直是在做重复工作,写过不计其数的Excel导入程序,每次只是满足于问题解决,后来终于找到一个方法,实现通用的Excel数据导入. 设计通用的Excel导入功能,第一个实现要求是不能依赖Excel,客户的电脑或服务器很有可能没有安装Excel,所以微软的Office Interop一

C# Excel导入、导出

C# Excel导入.导出 本篇主要介绍C#的Excel导入.导出. 目录 1. 介绍:描述第三方类库NPOI以及Excel结构 2. Excel导入:介绍C#如何调用NPOI进行Excel导入,包含:流程图.NOPI以及C#代码 3. Excel导出:介绍C#如何调用NPOI进行Excel导出,包含:流程图.NOPI以.C#代码以及代码分析 4. 源码下载:展示运行图及源码下载 1. 介绍 1.1 第三方类库:NPOI 说明:NPOI是POI项目的.NET 版本,可用于Excel.Word的读

开发指南专题十五:JEECG微云快速开发平台EXCEL导入导出

 开发指南专题十五:JEECG微云快速开发平台EXCEL导入导出 14.EXCEL导入导出 Excel的导入导出抽取通用功能,简化大家对POI的操作,对实体对象进行简单的注解配置就可以完成导入导出,模板的使用更是可以让打造漂亮的Excle报表,从而使大家从重复的工作中解脱出来,更加关注与业务的处理. 14.1注解介绍    注解名 作用对象 描述 是否必须 Excel 字段 对Excel字段的cell属性设置 是 ExcelCollection 字段 对集合对象进行标记表示一对多导出 否 E

C# Excel导入导出

目录 1. 介绍:描述第三方类库NPOI以及Excel结构 2. Excel导入:介绍C#如何调用NPOI进行Excel导入,包含:流程图.NOPI以及C#代码 3. Excel导出:介绍C#如何调用NPOI进行Excel导出,包含:流程图.NOPI以.C#代码以及代码分析 4. 源码下载:展示运行图及源码下载 1. 介绍 1.1 第三方类库:NPOI 说明:NPOI是POI项目的.NET 版本,可用于Excel.Word的读写操作. 优点:不用装Office环境. 下载地址:http://np

Java实现Excel导入数据库,数据库中的数据导入到Excel

实现的功能: Java实现Excel导入数据库,如果存在就更新 数据库中的数据导入到Excel 1.添加jxl.jar mysql-connector-java.1.7-bin.jar包到项目的lib目录下­ 2.Excel文件目录:D://book.xls 3.数据库名:javenforexcel 4.表名:stu 5.编写类:连接mysql的字符串方法.插入的方法.实体类­­ 表结构如下 : 连接数据库的工具类 package com.javen.db; import java.sql.Co

【高效程序员系列】2、别做机器人——让工作自动化

http://blog.csdn.net/jmshl/article/details/6764422 目录(?)[-] VS代码段的使用和定义 1Snippet Editor下载地址 Properties Code References Imports 2SnippetDesignerSetup-For VS2008msi下载地址 3SnippetDesigner-For VS2010vsix下载地址 代码段编译Snippet Compiler SQL智能提示和代码段 代码自动生成 脚本工具 1

05_Excel操作_03_模拟Web环境的Excel导入

[思路简述] 本文继续上一篇文章,上一篇中生成了“D://用户列表.xls”的excel文件,我们接下来将这个excel导入,然后显示在控制台上. 工程什么的都同上一篇文章,只是在ExcelService.java中添加了一个inputExcel()的方法,如下: [ExcelService.java] @Test public void inputExcel(){ File userExcel=new File("D:\\用户列表.xls"); try { FileInputStre