easyExcel需要的依赖的pom内容;easyExcel需要对应的poi版本,下面这个是一套;否则会报错;
(异常java.lang.NoSuchMethodError: org.apache.poi.ss.usermodel.Font.setBold(Z)V)
<dependency>
	<groupId>org.apache.poi</groupId>
	<artifactId>poi</artifactId>
	<!--<version>3.8</version>-->
	<version>3.17</version>
</dependency>
<dependency>
	<groupId>org.apache.poi</groupId>
	<artifactId>poi-ooxml</artifactId>
	<version>3.17</version>
	<!--<version>3.8</version>-->
</dependency>
<!-- easyExcel处理excel -->
<dependency>
	<groupId>com.alibaba</groupId>
	<artifactId>easyexcel</artifactId>
	<version>1.1.2-beta5</version>
</dependency>
--------------
往excel中写内容:
OutputStream os = new FileOutputStream(new File("C:/Users/zwk/Desktop/测试easyExcel.xlsx"));
ExcelWriter writer = EasyExcelFactory.getWriter(os);
com.alibaba.excel.metadata.Sheet sheet = new com.alibaba.excel.metadata.Sheet(1, 0, ModelBrand.class);
sheet.setSheetName("测试表");
writer.write(modelBrandMapper.getBrandList(), sheet);
writer.finish();
os.close();
注:ModelBrand是插入到excel中的对象模型;这里没有添加首页标题,是再ModelBrand类中定义的,且这个类是要继承BaseRowModel类;modelBrandMapper.getBrandList()是数据集合;
public class ModelBrand extends BaseRowModel {
    @ExcelProperty(value="id",index=0)
    private Long bId;
    @ExcelProperty(value="品牌",index=1)
    private String brand;
    @ExcelProperty(value="图片",index=2)
    private String img;
    @ExcelProperty(value="状态",index=3)
    private Short status;
    @ExcelProperty(value="备注",index=4)
    private String remark;
    @ExcelProperty(value="首字母",index=5)
    private String initial;
} value是导出列标题名称,index是列字段位置;
-------------
//导出excel表格(web项目)
@RequestMapping("/easyExcelTest")
public void easyExcelExport(HttpServletResponse response)throws Exception{
	String filename = "easyeexcel列表";
	response.setContentType("application/force-download");
	response.setHeader("Content-Disposition", "attachment;filename=\"" + java.net.URLEncoder.encode(filename, "UTF-8") + ".xlsx" + "\" ");
	//OutputStream os = new FileOutputStream(new File("C:/Users/zwk/Desktop/测试easyExcel.xlsx"));
	ExcelWriter writer = EasyExcelFactory.getWriter(response.getOutputStream());
	com.alibaba.excel.metadata.Sheet sheet = new com.alibaba.excel.metadata.Sheet(1, 0, ModelBrand.class);
	sheet.setSheetName("测试表");
	writer.write(modelBrandMapper.getBrandList(), sheet);
	writer.finish();
	response.getOutputStream().close();
}
----------------
读取excel文件数据:这里ModelInfoCopyMapper需要注入进来;这里使用构造方法将该参数传递进来
/**
 * 异步读取excel文件中的数据;
 * 读取excel文件中的指定数量,分批处理excel文件,解决占用内存的问题。
 * 利用poi当遇到表格数据是数值时,实际类中定义的是字符串,读取的时候就需要
 * 指定读取单元格的类型;而利用easyExcel模型无需这样,可以为空,null,数值类型,无需特别处理。
 * @Author:
 * @Date: 2019/10/16 11:58
 * @Version 1.0.0
 * @Description
 */

public class ExcelModelListener extends AnalysisEventListener<ModelInfoCopy> {
    private ModelInfoCopyMapper modelInfoCopyMapper;
    public ExcelModelListener(ModelInfoCopyMapper modelInfoCopyMapper){
        this.modelInfoCopyMapper = modelInfoCopyMapper;
    }
    public ExcelModelListener(){

    }
    //public static  ModelInfoCopyMapper modelInfoCopyMapper = SpringBeanUtil.getBean(ModelInfoCopyMapper.class);
    //一次读取50条数据,处理50条可以根据具体情况读取(若数据大,可以调整一次读取2000条数据);
    private static final int BATCH_COUNT = 2000;
    List<ModelInfoCopy> list = new ArrayList<>();
    private static int count = 0;

    @Override
    public void invoke(ModelInfoCopy modelInfoCopy, AnalysisContext analysisContext) {
        //System.out.println("解析到一条数据:"+modelBrand.toString());
        list.add(modelInfoCopy);
        count++;
        if(list.size() >= BATCH_COUNT){
            saveData(count);
            //清理list占用内存空间
            list.clear();
        }
    }

    @Override
    public void doAfterAllAnalysed(AnalysisContext analysisContext) {
        //这个方法调用若注释了,那么最后一批的数据就不会处理
        saveData(count);
       System.out.println("所有数据解析完成!"+"共处理"+count+"条数据");
    }
    //处理数据的方法
    private void saveData(int count){
        System.out.println(count+"条数据,开始存储数据库");
        for(ModelInfoCopy modelInfoCopy : list){
            modelInfoCopyMapper.insert(modelInfoCopy);
            //System.out.println(modelBrand.getbId()+","+modelBrand.getBrand()+","+modelBrand.getRemark());
        }

        System.out.println("存储数据库成功");
    }

}
//调用方法:这里处理十万数据,添加到数据库中需要206946毫秒,40个字段;30万条数据需要10分钟。
//使用poi处理的话,4万数据就会出现内存溢出异常。
@Test
public void test16(){

	String filePath = "C:/Users/zwk/Desktop/车型数据(含编码)20191014.xlsx";
	try{
		long beforTime = System.currentTimeMillis();
		com.alibaba.excel.metadata.Sheet sheet = new com.alibaba.excel.metadata.Sheet(1,1,ModelInfoCopy.class);
		EasyExcelFactory.readBySax(new FileInputStream(new File(filePath)),sheet ,new ExcelModelListener(modelInfoCopyMapper) );
		System.out.println("读取数据所花的时间:"+(System.currentTimeMillis()-beforTime)+"毫秒");
	}catch (Exception e){
		e.printStackTrace();
	}
}
注:com.alibaba.excel.metadata.Sheet(1,1,ModelInfoCopy.class);是从第二行读取的,过滤调了标题行;第一个”1“代表的是excel文件中的第一个表格;第二个”1“代表表格的第几行开始读取。

  

/**
* @Author: 普通类获取spring容器中的bean
* @Date: 2019/10/16 14:42
* @Version 1.0.0
* @Description
*/
public class SpringBeanUtil {

//将管理上下文的applicationContext设置成静态变量,供全局调用
public static ConfigurableApplicationContext applicationContext;
//定义一个获取已经实例化bean的方法
public static <T> T getBean(Class<T> c){
return applicationContext.getBean(c);
}
}

 

posted on 2019-10-16 15:43  lazyli  阅读(6637)  评论(0编辑  收藏  举报