java解析导入excel表格转为实体类javabean,可处理大数据量文件

原创 2018年04月17日 09:14:20

最近公司需求解析excel,一开始使用poi做的挺好的,后来直接上了几十万条数据的excel文件,内存直接溢出了,网上查到apache poi还提供了专门处理海量数据的方法,使用sax解析,果然用了内存使用率下降,但是不能解析xls文件,只能解析xlsx文件,所以把工具简单封装了一下,如果是xls的用传统方式解析,如果是xlsx的大文件,用sax,这样灵活一定,详见md文件

https://github.com/hellojamie/ebatis

Ebatis

用于解析excel表格内容到 java bean
目前支持xls、xlsx格式文件
对于大数据量文件自动使用sax方式解析,防止内存溢出

email:hello_jamie@outlook.com

目录(记得看注意):

  1.  开始
  2. 扩展功能
  3.  注意
开始

将jar加入到项目中
可以访问百度网盘下载
https://pan.baidu.com/s/1qSLXiaCWYg--0SELaiJWhA
[点击链接]
// Maven导入第三方poi依赖,或者直接把master pull下来发布到本地
<dependency>
    <groupId>org.apache.poi</groupId>
    <artifactId>poi</artifactId>
    <version>3.17</version>
</dependency>
<dependency> 
    <groupId>org.apache.poi</groupId>
    <artifactId>poi-ooxml</artifactId>
    <version>3.17</version>
</dependency>
<dependency>
	    <groupId>xerces</groupId>
	    <artifactId>xercesImpl</artifactId>
	    <version>2.9.1</version>
</dependency>

首先你需要创建好你的实体类,假设现在有这样一个excel表格需要解析

姓名手机号生日
王文娟188888888881996-01-01
大美丽166666666661996-01-01
首先你需要一个实体类
有几点要求,必须正确封装,包含get\set方法

属性上包含必要的Mapping注解,key属性填入与表格对应的名称,属性类型根据需要自己定义

public class People {
	
	@Mapping(key = "姓名")
	private String name;
	
	@Mapping(key = "手机号")
	private String phone;
	
	@Mapping(key = "生日")
	private Date birth;

	public String getName() {
		return name;
	}

	public void setName(String name) {
		this.name = name;
	}

	public String getPhone() {
		return phone;
	}

	public void setPhone(String phone) {
		this.phone = phone;
	}

	public Date getBirth() {
		return birth;
	}

	public void setBirth(Date birth) {
		this.birth = birth;
	}
	
}

然后将你的文档以流的方式加载进来(InputStream),通过以下代码开始解析

Init<People> init = new Init<People>(inputStream, new People(), false);
ActionContext<People> act = init.start();

  • Init接受一个InputStream对象,以及一个实体对象
  • 调用start开始
  • 通过ActionContext获取需要的信息,三个参数分别是(流信息,实体,是否去重)

注意:如果要去重的话请重写实体中的hashCode和equals方法,内部使用set来去重,false表示不去重)

ActionContext中包含了所需要的所有信息,信息格式如下,这里以json的形式展示

{
  "sheets":[
    {
      "line":2,
      "sheetName":"Sheet1",
      "column":3,
      "correctLine":2,
      "blankLineSize":0,
      "errorLineSize":0,
      "repeatLineSize":0,
      "info":[
        {
          "date":1331481600000,
          "name":"王文娟",
          "phone":"15035214458"
        },
        {
          "date":1331481600000,
          "name":"大美丽",
          "phone":"14555874458"
        }
      ],
		"blankLine":[

      ],
      "errorLine":[

      ],
      "repeatLine":[
        
      ]
    }
  ],
  "fileType":"XLSX",
  "fileSizeByte":9045,
  "useSax":false,
  "distinct":true,
  "result":true,
  "sheetSize":1
}
属性名含义
sheetssheet数组
line解析当前sheet一共多少行数据,不算表头
sheetNamesheet的名称
column列数(以扫描到的第一个空列之前的列数为准)
info实体对象数组,包含实体的列表,也就是行数据
correctLine实际正确解析出的数量(行数)
blankLineSize空行数量
errorLineSize错误行数量(正则不通过、解析失败等)
repeatLineSize重复行数量
blankLine空白行的行号-数组(不算表头)
errorLine错误行的行号-数组(不算表头)
repeatLine重复行的行号-数组(不算表头)
fileType文件类型
fileSizeByte文件大小(字节)
useSax是否使用了sax方式
distinct是否去重
result最后是否解析成功,如果中间出错则是false
sheetSize文件中有几个sheet

使用ActionContext的getXXX方法获取上面的内容

扩展功能

@Mapping注解有两个非必选属性

属性名含义是否必填
key填写与excel文件头的映射名称必填
rex填写解析内容时使用的正则表达式,如果不符合正则则不赋值非必填
delNull如果正则验证失败,该属性为null,是否删除整条信息,默认false不删除非必填

@LineNumber注解,获取当前记录是第几行,不算表头那行

@LineNumber
private Integer line;

@MappingSheetName注解,将sheet名称作为属性值添加

@MappingSheetName
private String type;

注意

因为工具还不是很完善,需要注意以下几点:

  1. 实体中请使用包装类,不支持int等类型,请使用Integer
  2. 如果excel文件有多个sheet,sheet间的表头应一致,不然会出现sheet之间解析的数据不一致
  3. 列与列之间不能包含表头为空的列,即不能有空列将信息隔开,如果有,以空列前一列为末尾解析
  4. excel文件请使用第一行表头,其余行信息的标准格式,如果有合并单元格情况,可能会解析失败(可以包含空行和空单元格,会自动过滤,但必须有表头)
  5. 目前默认10M以内使用poi传统方式解析,超过10M且为xlsx的文件将使用sax方式解析
  6. 实体类的属性不严格要求与列的数量一致,根据需要添加映射注解即可
  7. 实体类 的属性和表头的顺序没有严格要求,只要key匹配即可
  8. 如果需要去重,请重写实体的hashCode和equals方法,内部使用HashSet方式去重,重写时请注意
  9. 最后是否解析成功请以result属性为准

使用Poi读取大数据量excel的方法

  • 2015年02月09日 10:56
  • 10.46MB
  • 下载

JAVA读大数据量Excel

JAVA读大数据量Excel,对Excel各种类型的单元格数据进行分类处理,最后封装到一个类中。 只需要传入Excel文件即可进行逐行读取内容...
  • zp19890228
  • zp19890228
  • 2014-12-09 13:05:28
  • 5864

Javabean 实体类转换为xml

public static String getBeanXml(Object object){ String xml = null; try { JAXBContext conte...
  • gaoleijie
  • gaoleijie
  • 2016-10-18 20:31:45
  • 811

AS插件开发之Excel转JavaBean字段

.. 展示效果如上图所示。 我们就简单说一下AS或者是说IDEA的插件开发。我们可能都用过一些AS的插件,我比较喜欢也执迷其中的就是一些自动生成代码的插件,解放双手的感觉让人欲罢不能。 1.环境...
  • AndroidMsky
  • AndroidMsky
  • 2017-06-12 09:37:02
  • 1013

Java 中 Map与JavaBean实体类之间的相互转化

在做导入的时候,遇到了需要将map对象转化 成javabean的问题,也就是说,不清楚javabean的内部字段排列,只知道map的 key代表javabean的字段名,value代表值。 那现...
  • weinichendian
  • weinichendian
  • 2016-09-24 13:56:13
  • 15680

Java读取Excel表格到对象

Java读取Excel表格到对象 在公司的项目中,要求我把医疗人员传过来的excel表格资料通过系统解析成对象并且存到数据库,在学习了相关资料后,就开始了编写,代码如下:public List ...
  • havetogg
  • havetogg
  • 2017-03-01 14:53:03
  • 1746

excel表格数据转换成javaBean

  • 2012年05月24日 15:11
  • 28KB
  • 下载

poi根据导入的excel数据自动封装成bean对象集合

又是很久没写博客了,最近在弄一个批量导入的功能,按照古老的做法,当然是一行一行的解析然后根据字段所在的下标或者一列一列的解析依次赋值给bean对象。但是这种古老的方法弊端确实太多,于是想弄一个,根据表...
  • II_bat
  • II_bat
  • 2016-07-11 16:25:50
  • 5292

动态从excel取出数据,并封装动态javabean存入数据库

用户表 public class Userinfo implements Serializable { private static final long serialVersionUID = 1...
  • qq372577751
  • qq372577751
  • 2016-06-03 17:57:01
  • 868

JSP import JavaBean 无法解析导入

今天学习Jsp与JavaBean的使用时碰到的问题,记录一下以免以后忘记 问题详述 新建了一个Dynamic Web Project 工程 在WenContent文件下增加FirstJsp.jsp 文...
  • yangmx_5
  • yangmx_5
  • 2017-04-15 11:22:32
  • 1538
收藏助手
不良信息举报
您举报文章:java解析导入excel表格转为实体类javabean,可处理大数据量文件
举报原因:
原因补充:

(最多只允许输入30个字)