java 通过注解,反射,poi 生成Excel

最近公司项目需要把数据通过Excel形式展示给用户,由于第一次接触java 生成Excel,在网上找了很多资料,但是很多都不是很理想,自己设计了一个通过自定义注解把列名配置到实体类上,然后通过代码读取自定义注解作为列名,具体实现可以看一下代码(代码是实习时候写的,有点low,大家凑合着看吧,该功能已经上生产了,代码应该问题没什么问题了,就是不够优雅)

实体类

package com.ifp.business.common.utils;
import java.beans.BeanInfo;
import java.beans.IntrospectionException;
import java.beans.Introspector;
import java.beans.PropertyDescriptor;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.lang.reflect.Field;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

import org.apache.poi.hssf.usermodel.HSSFCell;
import org.apache.poi.hssf.usermodel.HSSFCellStyle;
import org.apache.poi.hssf.usermodel.HSSFFont;
import org.apache.poi.hssf.usermodel.HSSFRow;
import org.apache.poi.hssf.usermodel.HSSFSheet;
import org.apache.poi.hssf.usermodel.HSSFWorkbook;
import org.apache.poi.ss.util.CellRangeAddress;

import com.ifp.common.common.utils.ColumnName;

@SuppressWarnings("all")
public class CreateExcelTool {
    private static HSSFWorkbook workbook = null;
    private  List listAll = new ArrayList();
    private  List<Map> listMap = null;
    private  Map mapTitle = new  HashMap();
    private static String type[] = {"long","int","double","float","short","byte","boolean","char"};
    /** 
     * 判断文件是否存在. 
     * @param fileDir  文件路径 
     * @return 
     */  
    public static boolean fileExist(String fileDir){  
         boolean flag = false;  
         File file = new File(fileDir);  
         flag = file.exists();  
         return flag;  
    }  
    /** 
     * 判断文件的sheet是否存在. 
     * @param fileDir   文件路径 
     * @param sheetName  表格索引名 
     * @return 
     */  
    public static boolean sheetExist(String fileDir,String sheetName) throws Exception{  
         boolean flag = false;  
         File file = new File(fileDir);  
         if(file.exists()){    //文件存在  
            //创建workbook  
             try {  
                workbook = new HSSFWorkbook(new FileInputStream(file));  
                //添加Worksheet(不添加sheet时生成的xls文件打开时会报错)  
                HSSFSheet sheet = workbook.getSheet(sheetName);    
                if(sheet!=null)  
                    flag = true;  
            } catch (Exception e) {  
                throw e;
            }   
              
         }else{    //文件不存在  
             flag = false;  
         }  
         return flag;  
    }  
    /** 
     * 创建新excel. 
     * @param fileDir  excel的路径 
     * @param sheetName 要创建的表格索引 
     * @param list excel的第一行即列名 
     */  
    public static void CreateExcelTitle(String fileDir,String sheetName,List list,String name) throws Exception{
        //CreateExcelUtil.deleteExcel(fileDir);
        System.out.println("Excel路径:----------------------------------------"+fileDir);
        String path = fileDir.substring(0,fileDir.lastIndexOf("\\")+1);
        if (getCurrentOS().equals("linux")) {
            path = fileDir.substring(0,fileDir.lastIndexOf("/")+1);
        }
        
        File file=new File(path);
        if(!file.exists()){
            file.mkdirs(); 
        }
        HSSFSheet sheet1;
        Map<String, String> sheetStyle = new HashMap<String, String>();  
        //判断文件是否存在
        if(CreateExcelUtil.fileExist(fileDir)){
            workbook = new HSSFWorkbook(new FileInputStream(fileDir));
            
            //判断sheet页是否存在
            if(CreateExcelUtil.sheetExist(fileDir, sheetName)){
                sheet1 = workbook.getSheet(sheetName);
            }else{
                //添加Worksheet(不添加sheet时生成的xls文件打开时会报错)
                sheet1 = workbook.createSheet(sheetName); 
            }
        }else{
             workbook = new HSSFWorkbook();
            //添加Worksheet(不添加sheet时生成的xls文件打开时会报错)  
            sheet1 = workbook.createSheet(sheetName); 
        }
        sheet1.autoSizeColumn(1); 
        sheet1.autoSizeColumn(1, true);
        /**合并单元格
         * 参数:起始行号,终止行号, 起始列号,终止列号
         * 只有 该文件中不存在sheet页才会合并单元格
         * */
        sheet1.addMergedRegion(new CellRangeAddress(0, 0, 0, list.size() - 1));
        sheet1.addMergedRegion(new CellRangeAddress(1, 1, 0, list.size() - 1));
        SimpleDateFormat format = new SimpleDateFormat("yyyy年M月");
        
        //新建文件  
        FileOutputStream out = null;  
        try {
            HSSFFont fontName = workbook.createFont();
            HSSFCellStyle cellStyleName = workbook.createCellStyle();
            fontName.setFontHeightInPoints((short) 14); //字体高度
            fontName.setFontName("宋体"); //字体
            fontName.setBoldweight(HSSFFont.BOLDWEIGHT_BOLD); //加粗
            cellStyleName.setAlignment(HSSFCellStyle.ALIGN_CENTER);
            cellStyleName.setFont(fontName);
            HSSFRow row1 = workbook.getSheet(sheetName).createRow(0);
            row1.setHeight((short)450);
            HSSFCell cell1 = row1.createCell(0);  
            cell1.setCellValue(name);
            cell1.setCellStyle(cellStyleName);
            //设置单元格为文本格式
            cell1.setCellType(HSSFCell.CELL_TYPE_STRING);
            HSSFRow row2 = workbook.getSheet(sheetName).createRow(1);
            HSSFCell cell2 = row2.createCell(0);  
            cell2.setCellValue("制表日期:"+format.format(new Date())); 
            
            //添加列名 
            HSSFRow row = workbook.getSheet(sheetName).createRow(2);    //创建第一行
            HSSFFont font = workbook.createFont();
            HSSFCellStyle cellStyle = workbook.createCellStyle();
            font.setFontHeightInPoints((short) 12); //字体高度
            cellStyle.setFont(font);
            for(short i = 0;i < list.size();i++){  
                HSSFCell cell = row.createCell(i);
                //设置列宽
                sheet1.setColumnWidth(i,list.get(i).toString().getBytes().length*256);
                cell.setCellValue("" + list.get(i)); 
                cell.setCellStyle(cellStyle);
            }  
            out = new FileOutputStream(fileDir);  
            workbook.write(out);  
        } catch (Exception e) {  
            throw e;
        } finally {    
            try {    
                out.close();    
            } catch (IOException e) {    
                e.printStackTrace();  
            }    
        }    
    } 
    /** 
     * 删除文件. 
     * @param fileDir  文件路径 
     */  
    public static boolean deleteExcel(String fileDir) {  
        boolean flag = false;  
        File file = new File(fileDir);  
        // 判断目录或文件是否存在    
        if (!file.exists()) {  // 不存在返回 false    
            return flag;    
        } else {    
            // 判断是否为文件    
            if (file.isFile()) {  // 为文件时调用删除文件方法    
                file.delete();  
                flag = true;  
            }   
        }  
        return flag;  
    }  
    /** 
     * 往excel中写入
     * @param fileDir    文件路径 
     * @param sheetName  表格索引 
     * @param object 
     * @throws Exception 
     */  
    public  void writeToExcel(String fileDir,String sheetName,List<Map> mapList) throws Exception{  
        //创建workbook  
        File file = new File(fileDir);  
        try {  
            workbook = new HSSFWorkbook(new FileInputStream(file));  
        } catch (FileNotFoundException e) {  
            e.printStackTrace();  
        } catch (IOException e) {  
            e.printStackTrace();  
        }  
        //流  
        FileOutputStream out = null;  
        HSSFSheet sheet = workbook.getSheet(sheetName);  
        HSSFFont font = workbook.createFont();
        HSSFCellStyle cellStyle = workbook.createCellStyle();
        font.setFontHeightInPoints((short) 12); //字体高度
        cellStyle.setFont(font);
        /*sheet.setDefaultColumnWidth(14);//设置默认列宽
        sheet.setDefaultRowHeight((short) (6 * 256)); //设置默认行高,表示2个字符的高度*/ 
       // 获取表格的总行数  
        // int rowCount = sheet.getLastRowNum() + 1; // 需要加一  
        // 获取表头的列数  
        int columnCount = sheet.getRow(2).getLastCellNum();  
        try {  
            // 获得表头行对象  
            HSSFRow titleRow = sheet.getRow(2);  
            if(titleRow!=null){
                int rowId = 3;
                int i = 0;
                int rowsIndex = 0;
                int row = 3;
                boolean flag = false;
                while(i<mapList.size()){
                    Map map = mapList.get(i);
                    HSSFRow newRow1=sheet.createRow(row);
                    for (short columnIndex = 0; columnIndex < columnCount; columnIndex++) {  //遍历表头  
                        String titleName = titleRow.getCell(columnIndex).toString().trim().toString().trim();
                        String mapKey = (String) mapTitle.get(titleName);
                        List list = new ArrayList();
                        if(map.get(mapKey)!=null&&map.get(mapKey).getClass().equals(list.getClass())){
                            flag = true;
                            list = (List) map.get(mapKey);
                            int j = 0;
                            HSSFRow newRow;
                            for(int listIndex = 0;listIndex<list.size();listIndex++){
                                if(sheet.getRow(rowId + j)!=null){
                                    newRow = sheet.getRow(rowId+j); 
                                }else{
                                    newRow=sheet.createRow(rowId+j);
                                }
                                newRow.setHeightInPoints(50);
                                HSSFCell cell = newRow.createCell(columnIndex);  
                                //设置列宽
                                sheet.setColumnWidth(i,list.get(listIndex).toString().getBytes().length*256);
                                cell.setCellValue(list.get(listIndex)==null ? null : list.get(listIndex).toString());
                                setStyle(cell,font);
                                j++;
                                rowsIndex = j;
                            }
                        }else{
                            try{
                                HSSFCell cell = newRow1.createCell(columnIndex);  
                                //判断字符串长度是否大于列宽,大于列宽,从新设置列宽
                                if(!"".equals(map.get(mapKey))&&map.get(mapKey)!=null){
                                    //判断是否是中文
                                    if(isContainChinese(map.get(mapKey).toString())&&sheet.getColumnWidth(columnIndex)<map.get(mapKey).toString().getBytes().length*256){
                                        
                                        sheet.setColumnWidth(columnIndex,map.get(mapKey).toString().getBytes().length*256);
                                        
                                    }else if(!isContainChinese(map.get(mapKey).toString())&&sheet.getColumnWidth(columnIndex)<map.get(mapKey).toString().getBytes().length*512){
                                        
                                        sheet.setColumnWidth(columnIndex,map.get(mapKey).toString().getBytes().length*512);
                                    }
                                }
                                    
                                cell.setCellValue(map.get(mapKey)==null ? null : map.get(mapKey).toString());
                                /*setStyle(cell,font);*/
                                
                                cell.setCellStyle(cellStyle);
                            }catch(Exception e){
                                System.out.println("------------------------------------空---------------------------");
                                e.printStackTrace();
                            }
                        }
                    }
                    if(flag){
                        row = row+rowsIndex;
                    }else{
                        row = row+rowsIndex + 1;
                    }
                    
                    rowId = row;
                    i++;
                }
                
            }  
            out = new FileOutputStream(fileDir);  
            workbook.write(out);  
        } catch (Exception e) {  
            e.printStackTrace();
        } finally {    
            try {    
                out.close();    
            } catch (IOException e) {    
                e.printStackTrace();  
            }    
        }    
    }
    /**  
     * 将一个 JavaBean 对象转化为一个 Map  
     * @param bean 要转化的JavaBean 对象  
     * @return 转化出来的 Map 对象  
     * @throws ClassNotFoundException 
     * @throws InstantiationException 
     * @throws IntrospectionException 如果分析类属性失败  
     * @throws IllegalAccessException 如果实例化 JavaBean 失败  
     * @throws InvocationTargetException 如果调用属性的 setter 方法失败  
     */    
   
    public static Map toMap(Object bean) throws ClassNotFoundException, InstantiationException {  
        Map<Object, Object> returnMap = new HashMap<Object, Object>();
        Class clazz = null;
        if(!bean.toString().contains("@")){
            try {
                clazz = Class.forName(bean + "");
                bean = clazz.newInstance();
            } catch (ClassNotFoundException e) {
                e.printStackTrace();
            } catch (InstantiationException e) {
                e.printStackTrace();
            } catch (IllegalAccessException e) {
                e.printStackTrace();
            }
        }else{
            clazz = bean.getClass();
            
        }
        StringBuffer sb = new StringBuffer();  
        BeanInfo beanInfo = null;    
        try {
            //得到的BeanInfo对象封装了把这个类当做JavaBean看的结果信息,即属性的信息
            beanInfo = Introspector.getBeanInfo(clazz);  
            //获取 clazz 类型中的 propertyName 的属性描述器  
            PropertyDescriptor[] propertyDescriptors = beanInfo.getPropertyDescriptors();  
            
            for (int i = 0; i < propertyDescriptors.length; i++) {
                
                PropertyDescriptor descriptor = propertyDescriptors[i];
                if("class".equals(descriptor.getName())){
                    continue;
                }
                String propertyType = descriptor.getPropertyType().toString();
                boolean boo = com.ifp.common.common.utils.StringUtil.isInList(propertyType, com.ifp.common.common.utils.StringUtil.arrayToList(type));
                        
                if(propertyType.contains("java.util.List")){
                    try {
                        Method readMethod = descriptor.getReadMethod();    
                        List result = null;  
                        //调用 set 方法将传入的value值保存属性中去  
                        result = (List) readMethod.invoke(bean, new Object[0]);
                       
                        for(Object o:result){
                            toMap(o);
                        }
                        
                    } catch (SecurityException e) {
                        e.printStackTrace();
                    }
                    continue;
                }else if(propertyType.contains("lang") || boo){
                    String propertyName = descriptor.getName(); 
                    if (!propertyName.equals("class")) {
                        Method readMethod = descriptor.getReadMethod();    
                        Object result = null;  
                        //调用 set 方法将传入的value值保存属性中去  
                        result = readMethod.invoke(bean, new Object[0]);
                        if (null != result) {
                            if(returnMap!=null&&returnMap.containsKey(propertyName)){
                                List list1 = new ArrayList();
                                List list2 = new ArrayList();
                                list1.add(result);
                                if(!returnMap.get(propertyName).getClass().equals(list2.getClass())){
                                    list2.add(returnMap.get(propertyName));
                                }else{
                                    list2 = (List) returnMap.get(propertyName);
                                }
                                
                                list1.addAll(list2);
                                result = list1;
                            }else{
                                result = result.toString(); 
                            }
                               
                        }
                        returnMap.put(propertyName, result);    
                    } 
                }else{
                    Object obj = propertyType.substring(propertyType.indexOf(" ") + 1);
                    Method readMethod = descriptor.getReadMethod();    
                    Object result = null;  
                    //调用 set 方法将传入的value值保存属性中去  
                    result = readMethod.invoke(bean, new Object[0]);
                    toMap(result);
                    continue;
                }
                   
            }    
        } catch (IntrospectionException e) {    
            System.out.println("分析类属性失败");    
        } catch (IllegalAccessException e) {    
            System.out.println("实例化 JavaBean 失败");    
        } catch (IllegalArgumentException e) {    
            System.out.println("映射错误");    
        } catch (InvocationTargetException e) {    
            System.out.println("调用属性的 setter 方法失败");    
        }    
        return returnMap;    
    }
    /**
     * 获取父类和当前类所有属性(包括private)
     * @param object
     * @return
     */
    public static List getAllFields(Object object){
          Class clazz = object.getClass();
          List fieldList = new ArrayList();
          while (clazz != null){
              for (Field field : clazz.getDeclaredFields()) {
                  if (field.getGenericType().toString().contains("java.util.List")){
                      Object obj = (Object)field.toString().substring(field.toString().lastIndexOf(".")+1);
                       Class clazzList = obj.getClass();
                          field.setAccessible(true);
                          String fieldName = field.getName();
                          fieldList.add(fieldName);
                  }
                   
                }
             
            clazz = clazz.getSuperclass();
          }
        
          return fieldList;
    }
    /**
     * 获得传入对象的所有属性名
     * @param object
     * @return
     */
    public  List getFields(Object object){
        Class cla = null;
        if(!object.toString().contains("@")){
            try {
                cla = Class.forName(object + "");
            } catch (ClassNotFoundException e) {
                e.printStackTrace();
            }
        }else{
            cla = object.getClass();
        }
        
        for(Field field : cla.getDeclaredFields()){
            boolean boo = com.ifp.common.common.utils.StringUtil.isInList(field.getGenericType().toString(), com.ifp.common.common.utils.StringUtil.arrayToList(type));
            //判断该字段的声明类型
            if(field.getGenericType().toString().contains("java.util.List")){
                Object obj = (Object)(field.getGenericType().toString().substring(field.getGenericType().toString().indexOf("<")+1,field.getGenericType().toString().indexOf(">")));
                getFields(obj);
                continue;
            }else if(field.getGenericType().toString().contains("lang") || boo){
                field.setAccessible(true);
                //获取自定义注解
                ColumnName anno = field.getAnnotation(ColumnName.class);
                String fieldName = field.getName();
                String annoValue = null;
                if(anno == null){
                    /*annoValue = fieldName;
                    mapTitle.put(fieldName, fieldName);*/
                    //如果该字段没有注解,直接跳过,表格中不会显示此字段
                    continue;
                }else{
                    annoValue = anno.value();
                    mapTitle.put(anno.value(),fieldName);
                }
                listAll.add(annoValue);
            }else{
                Object obj = field.getGenericType().toString().substring(field.getGenericType().toString().indexOf(" ") + 1);
                getFields(obj);
                continue;
            }
            
        }
        
     
      return listAll;
    }
    /**
     * 判断字符串是否包含中文
     * @param str
     * @return
     */
    public static boolean isContainChinese(String str) {
        Pattern p = Pattern.compile("[\u4e00-\u9fa5]");
        Matcher m = p.matcher(str);
        if (m.find()) {
            return true;
        }
        return false;
    }
    //设置字体样式
    public static void setStyle(HSSFCell cell,HSSFFont font){
         // 设置字体
       
        font.setFontHeightInPoints((short) 12); //字体高度
        //font.setColor(HSSFFont.COLOR_RED); //字体颜色
        //font.setFontName("楷体"); //字体
        //font.setBoldweight(HSSFFont.BOLDWEIGHT_BOLD); //宽度
        //font.setItalic(true); //是否使用斜体
        //font.setStrikeout(true); //是否使用划线
        // 设置单元格类型
        HSSFCellStyle cellStyle = workbook.createCellStyle();
        cellStyle.setFont(font);
       // cellStyle.setAlignment(HSSFCellStyle.ALIGN_CENTER); //水平布局:居中
        //cellStyle.setWrapText(true);
        cell.setCellStyle(cellStyle);
    }
    public static String getCurrentOS() {
        String system = "";
        int OS = System.getProperty("os.name").toUpperCase().indexOf("WINDOWS");
        if (OS != -1) {
            system = "windows";
        } else
            system = "linux";
        return system;
    }
    /**
     * 
     * @param fileDir
     * @param sheetName  sheet页名字
     * @param mapList
     * @throws Exception 
     */
    public  void createExcel(String fileDir,String sheetName,List<Object> list, String name ) throws Exception{
        listMap = new ArrayList();
        List titleList = new ArrayList();
        CreateExcelTool CreateExcelTool = new CreateExcelTool();
        for(Object obj : list){
            listMap.add(toMap(obj));
        } 
        //System.out.println(listMap);
        titleList = CreateExcelTool.getFields(list.get(0));
        System.out.println("表头:"+titleList);
        CreateExcelTool.CreateExcelTitle(fileDir, sheetName, titleList,name);
        CreateExcelTool.writeToExcel(fileDir, sheetName,listMap);
        System.out.println("---------------------------------------生成表格成功-------------------------------------");
    }
   
    public static void main(String[] args) throws Exception {  
      
        List<Object> list=new ArrayList<Object>();
        List<Object> list2=new ArrayList<Object>();
        Map<String,String> map=new HashMap<String,String>();
        
/*      for(int i = 0;i<3;i++){
          Person p = new Person();
          p.setName("2018-01-16 00:00:00.0"+i);
          p.setAge("2018-01-16 00:00:00.0");
          p.setSex("2018-01-16 00:00:00.0"+i);
            list.add(p);
        }
      for(int i = 0;i<3;i++){
          person2 p = new person2();
          p.setName("list2少时诵诗书所所所所所所所所所所所所所所"+i);
            list2.add(p);
        }*/
      CreateExcelTool CreateExcelTool = new CreateExcelTool();
      String path ="E:/excel/123456778.xls";
      CreateExcelTool.createExcel(path, "sheet1", list, "测试1");
      CreateExcelTool.createExcel(path, "sheet2", list2, "测试2");
    }  
}
自定义注解

package com.ifp.common.common.utils;

import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.ElementType;
import java.lang.annotation.Target;
/**
 * 自定义注解,程序可以读取注解values(该程序主要用于生成表格时,通过读取类属性中配置的注解,生产表格列名)
 * @author cdy
 * @Retention(RetentionPolicy.RUNTIME) 表示该注解在jvm运行时存在
 *@Target(ElementType.FIELD) 只可以修饰属性
 */
@Retention(RetentionPolicy.RUNTIME)  
@Target(ElementType.FIELD)
public @interface ColumnName {

    String value();
}
 

  • 2
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值