zoukankan      html  css  js  c++  java
  • Excel通用类工具(一)

    avatar

    前言

    最近项目中遇到要将MySQL数据库中的某些数据导出为Excel格式保存,在以前也写过这样的功能,这次就准备用以前的代码,但是看了一下,这次却不一样,因为在以前用到的都是导出一种或几种数据,种类不多,但是这次导出的种类比较多,相当于就是每一种类型的数据得单独写一些代码,而且重复的比较多;就想写一个通用的,不管什么种类,直接传入数据就行了;

    正文

    想法

    因为数据的种类是不同的,里面的属性也各不相同,如何用同一段代码去处理这些不同种类的属性,让我第一时间想到了Java的泛型和反射;因为之前的笔记中就写到了反射,这时候刚好派上用场,就来实际操作一下;

    代码部分

    首先导入poi相应的jar包:

    
            <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>org.apache.poi</groupId>
                <artifactId>poi-ooxml-schemas</artifactId>
                <version>3.17</version>
            </dependency>
            
    
    1. 实体类
      有两个实体类:pojoA 和pojoBB,主要是为了测试不同实体类的不同属性是否有效;
      pojoA:
    
     /**
     * @author gyc
     * @date 2018/10/26  21:50
     */
     
    public class PojoA {
        private String name;
        private int num;
        private double price;
        public String getName() {
            return name;
        }
        public void setName(String name) {
            this.name = name;
        }
        public int getNum() {
            return num;
        }
        public void setNum(int num) {
            this.num = num;
        }
        public double getPrice() {
            return price;
        }
        public void setPrice(double price) {
            this.price = price;
        }
    }
        
    

    pojoB:

    
    /**
     * @author gyc
     * @date 2018/10/26  21:51
     */
    public class PojoB {
        private String userName;
        private int age;
        private Date birthday;
        public String getUserName() {
            return userName;
        }
        public void setUserName(String userName) {
            this.userName = userName;
        }
        public int getAge() {
            return age;
        }
        public void setAge(int age) {
            this.age = age;
        }
        public Date getBirthday() {
            return birthday;
        }
        public void setBirthday(Date birthday) {
            this.birthday = birthday;
        }
    }
    
    
    1. 核心代码部分
      使用该类时,需要传入每列得列名,为String数组,以及数据的List集合对象;还有一个Excel的title名;其中每列自动适应宽度,这个属性得将数据存入Excel之后才能调用,如果在数据存入之前调用,则不会取作用;
    
    /**
     * @author gyc
     * @date 2018/10/26  21:45
     */
    public class ExcelUtil<T> {
    
        public HSSFWorkbook setExcel(String title,String[] columnNames, List<T> tList) throws NoSuchMethodException, IllegalAccessException, InvocationTargetException, IOException {
    //        1.创建Excel工作薄对象
            HSSFWorkbook workbook=new HSSFWorkbook();
    //        2.创建Excel工作表对象
            HSSFSheet sheet=workbook.createSheet(title);
            HSSFRow row=null;
    //        3.创建Excel工作表的第一行,并填充列名
            row=sheet.createRow(0);
            for(int i=0;i<columnNames.length;i++){
                row.createCell(i).setCellValue(columnNames[i]);
            }
            Field[] declaredFields = tList.get(0).getClass().getDeclaredFields();
    //        4.将数据填充至表格中
            for(int j=1;j<=tList.size();j++){
                T t= tList.get(j-1);
                row=sheet.createRow(j);
                for(int i=0;i<declaredFields.length;i++){
                    // 通过反射获取属性值
                    String fieldName = declaredFields[i].getName();
                    String getMethodName="get"+fieldName.substring(0,1).toUpperCase()+fieldName.substring(1);
                    Method declaredMethod = t.getClass().getDeclaredMethod(getMethodName);
                    //执行方法
                    Object fieldValue = declaredMethod.invoke(t);
                    //判断是否为空
                    if(fieldValue!=null &&  !"".equals(fieldValue)){
                        //判断属性值类型
                        if(fieldValue instanceof Integer){
                            row.createCell(i).setCellValue(Integer.valueOf(fieldValue.toString()));
                        }else if(fieldValue instanceof Double){
                         row.createCell(i).setCellValue(Double.valueOf(fieldValue.toString()));
                        }else if(fieldValue instanceof Date){
                            row.createCell(i).setCellValue(new SimpleDateFormat("yyyy-MM-dd hh:mm:ss").format(fieldValue));
                        }else {
                           row.createCell(i).setCellValue(fieldValue.toString());
                        }
                    }else {
                        row.createCell(i).setCellValue("");
                    }
                }
            }
    //       自动设置列宽,要在在数据读入之后设置;
            for (int i = 0; i < columnNames.length; i++) {
                sheet.autoSizeColumn(i);
                //在自动适应的基础上增加宽度
    //            sheet.setColumnWidth(i,sheet.getColumnWidth(i)*17/10);
            }
            return workbook;
        }
    }
    
    

    测试

    测试代码

    
    /**
     * @author gyc
     * @date 2018/10/26  21:52
     */
    public class Test {
        public static void main(String[] args) throws InvocationTargetException, NoSuchMethodException, IllegalAccessException, IOException {
            PojoA pojoA=new PojoA();
            pojoA.setName("a");
            pojoA.setNum(1);
            pojoA.setPrice(1.1234);
            List<PojoA> lista=new ArrayList<>();
            lista.add(pojoA);
    
            PojoB pojoB=new PojoB();
            pojoB.setUserName("b");
            pojoB.setAge(2);
            pojoB.setBirthday(new Date());
            List<PojoB> listb=new ArrayList<>();
            listb.add(pojoB);
    
            HSSFWorkbook workbooka = new ExcelUtil().setExcel("pojoA", new String[]{"名称", "数量", "价格"}, lista);
            HSSFWorkbook workbookb = new ExcelUtil().setExcel("pojoB", new String[]{"名称", "年龄", "时间"}, listb);
    
            workbooka.write(new FileOutputStream(new File("/Users/rose/IdeaProjects/java-study/smalltools/pojoA.xls")));
            workbookb.write(new FileOutputStream(new File("/Users/rose/IdeaProjects/java-study/smalltools/pojoB.xls")));
        }
    }
    
    

    GitHub地址:

    总结

    本篇笔记中使用了Java泛型和反射,但都是用得比较浅,只是最基础的使用;主要解决了处理数据种类繁多的的问题,不用单独处理;
    其中也有很多不足之处,如下:

    • 数据集合只支持List集合
    • 用到了反射,速率可能比单独处理的低
    • 需要手动传入列名,比较硬编码
  • 相关阅读:
    saltstack推送文件到节点
    Linux查看僵尸进程
    Linux批量对某个目录下特定文件进行修改内容
    Linux查看网络连接数
    Linux查看当前目录下哪个目录占用容量最多
    Linux查看inodes最多的目录
    Linux用命令过滤出ip地址
    mysql表字段的增删改操作
    Python安装模块超时
    sql 查询结果中加入空值列
  • 原文地址:https://www.cnblogs.com/guoyuchuan/p/9941119.html
Copyright © 2011-2022 走看看