excel導出導入(poi+反射+註解)

描述:使用註解建立實體與excel之間的映射關係,反射設置實體屬性值

一、jar包
二、定義註解
三、定義測試實體
四、封裝excel工具類

一、jar包

poi-3.17.jar
poi-excelant-3.17.jar
poi-ooxml-3.17.jar
poi-ooxml-schemas-3.17.jar

maven導入

<!-- poi-ooxml自動引入操作xlsx文件所用到的其他包 -->
        <dependency>
            <groupId>org.apache.poi</groupId>
            <artifactId>poi-ooxml</artifactId>
            <version>3.15-beta2</version>
        </dependency>

二、定義註解

定義該註解作用:主要用來描述屬性存在excel中的第幾列,列名是什麼。目的是與excel建立關係。


/**
 * 定義excel描述註解
 * @author YZQ
 *
 */

@Retention(RetentionPolicy.RUNTIME)
public @interface MyAnnotation {

    /**
     * 列索引
     * @return
     */
    public int columnIndex() default 0;

    /**
     * 列名
     * @return
     */
    public String columnName() default "";

}

三、定義測試實體

public class ExcelEntity {

    public ExcelEntity() {
    }

    public ExcelEntity(int id, String name) {
        this.id = id;
        this.name = name;
    }
    //描述改屬性在excel中第0列,列名爲  序號
    @MyAnnotation(columnIndex=0,columnName="序號")
    private int id;

    //描述改屬性在excel中第1列,列寧爲 名字
    @MyAnnotation(columnIndex=1,columnName="名字")
    private String name;


    public int getId() {
        return id;
    }
    public void setId(int id) {
        this.id = id;
    }

    public String getName() {
        return name;
    }

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

    @Override
    public String toString() {
        return "ExcelEntity [id=" + id + ", name=" + name + "]";
    }
}

四、封裝excel工具類

excel導出(註釋很詳細,不解釋)

/**
     * 輸出excel文件
     * @param data 數據集合
     * @param path 輸出路徑
     */
    public static void outExcelFile(List<?> data, String path) {

        File file = new File(path);

        // 創建workbook
        HSSFWorkbook wb = new HSSFWorkbook();

        // 創建sheet
        Sheet sheet = wb.createSheet("sheel");

        // 創建表頭行
        Row row = sheet.createRow(0);

        // 創建單元格樣式
        HSSFCellStyle style = wb.createCellStyle();
        // 居中顯示
        style.setAlignment(HorizontalAlignment.CENTER);

        // 獲取實體所有屬性
        Field[] fields = data.get(0).getClass().getDeclaredFields();
        // 列索引
        int index = 0;
        // 列名稱
        String name = "";
        MyAnnotation myAnnotation;

        // 創建表頭
        for (Field f : fields) {
            // 是否是註解
            if (f.isAnnotationPresent(MyAnnotation.class)) {
                // 獲取註解
                myAnnotation = f.getAnnotation(MyAnnotation.class);
                // 獲取列索引
                index = myAnnotation.columnIndex();
                // 列名稱
                name = myAnnotation.columnName();
                // 創建單元格
                creCell(row, index, name, style);
            }
        }

        // 行索引  因爲表頭已經設置,索引行索引從1開始
        int rowIndex = 1;
        for (Object obj : data) {
            // 創建新行,索引加1,爲創建下一行做準備
            row = sheet.createRow(rowIndex++);
            for (Field f : fields) {
                // 設置屬性可訪問
                f.setAccessible(true);
                // 判斷是否是註解
                if (f.isAnnotationPresent(MyAnnotation.class)) {
                    // 獲取註解
                    myAnnotation = f.getAnnotation(MyAnnotation.class);
                    // 獲取列索引
                    index = myAnnotation.columnIndex();
                    try {
                        // 創建單元格     f.get(obj)從obj對象中獲取值設置到單元格中
                        creCell(row, index, String.valueOf(f.get(obj)), style);
                    } catch (IllegalArgumentException e) {
                        e.printStackTrace();
                    } catch (IllegalAccessException e) {
                        e.printStackTrace();
                    }
                }
            }
        }

        FileOutputStream outputStream = null;
        try {
            outputStream = new FileOutputStream(file);
            wb.write(outputStream);
        } catch (FileNotFoundException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        } finally {
            //釋放資源
            try {
                if (wb != null) {
                    try {
                        wb.close();
                    } catch (IOException e) {
                        e.printStackTrace();
                    }
                }
                if (outputStream != null) {
                    outputStream.close();
                }
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }

excel導入(註釋很詳細,不解釋)

/**
     * 讀取excel文件,並把讀取到的數據封裝到clazz中
     * 
     * @param path
     *            文件路徑
     * @param clazz
     *            實體類
     * @return 返回clazz集合
     */
    public static <T extends Object> List<T> readExcelFile(String path, Class<T> clazz) {
        // 存儲excel數據
        List<T> list = new ArrayList<>();
        FileInputStream is = null;

        try {
            is = new FileInputStream(new File(path));
        } catch (FileNotFoundException e1) {
            throw new RuntimeException("文件路徑異常");
        }

        Workbook wookbook = null;

        // 根據excel文件版本獲取工作簿
        if (path.endsWith(".xls")) {
            wookbook = xls(is);
        } else if (path.endsWith(".xlsx")) {
            wookbook = xlsx(is);
        } else {
            throw new RuntimeException("文件出錯,非excel文件");
        }

        // 得到一個工作表
        Sheet sheet = wookbook.getSheetAt(0);

        // 獲取行總數
        int rows = sheet.getLastRowNum() + 1;

        Row row;

        // 獲取類所有屬性
        Field[] fields = clazz.getDeclaredFields();

        T obj = null;
        int coumnIndex = 0;
        Cell cell = null;
        MyAnnotation myAnnotation = null;
        for (int i = 1; i < rows; i++) {
            // 獲取excel行
            row = sheet.getRow(i);
            try {
                // 創建實體
                obj = clazz.newInstance();
                for (Field f : fields) {
                    // 設置屬性可訪問
                    f.setAccessible(true);
                    // 判斷是否是註解
                    if (f.isAnnotationPresent(MyAnnotation.class)) {
                        // 獲取註解
                        myAnnotation = f.getAnnotation(MyAnnotation.class);
                        // 獲取列索引
                        coumnIndex = myAnnotation.columnIndex();
                        // 獲取單元格
                        cell = row.getCell(coumnIndex);
                        // 設置屬性
                        setFieldValue(obj, f, wookbook, cell);
                    }
                }
                // 添加到集合中
                list.add(obj);
            } catch (InstantiationException e1) {
                e1.printStackTrace();
            } catch (IllegalAccessException e1) {
                e1.printStackTrace();
            }

        }

        try {
            //釋放資源
            wookbook.close();
            is.close();
        } catch (IOException e) {
            e.printStackTrace();
        }
        return list;
    }

設置屬性值
這裏只寫部分,按自己需要自行添加

    /**
     * 設置屬性值
     * 
     * @param obj
     *            操作對象
     * @param f
     *            對象屬性
     * @param cell
     *            excel單元格
     */
    private static void setFieldValue(Object obj, Field f, Workbook wookbook, Cell cell) {
        try {
            if (f.getType() == int.class || f.getType() == Integer.class) {
                f.setInt(obj, getInt(cell));
            } else if (f.getType() == Double.class || f.getType() == double.class) {
                f.setDouble(obj, getDouble(null, cell));
            } else {
                f.set(obj, getString(cell));
            }
        } catch (IllegalAccessException e) {
            e.printStackTrace();
        }
    }

excel版本處理


    /**
     * 對excel 2003處理
     */
    private static Workbook xls(InputStream is) {
        try {
            // 得到工作簿
            return new HSSFWorkbook(is);
        } catch (IOException e) {
            e.printStackTrace();
        }
        return null;
    }

    /**
     * 對excel 2007處理
     */
    private static Workbook xlsx(InputStream is) {
        try {
            // 得到工作簿
            return new XSSFWorkbook(is);
        } catch (IOException e) {
            e.printStackTrace();
        }
        return null;
    }

剩下的是一些單元格創建、獲取單元格值

/**
     * 創建單元格
     * 
     * @param row
     * @param c
     * @param cellValue
     * @param style
     */
    private static void creCell(Row row, int c, String cellValue, CellStyle style) {
        Cell cell = row.createCell(c);
        cell.setCellValue(cellValue);
        cell.setCellStyle(style);
    }

測試效果:
這裏寫圖片描述

生成文件
這裏寫圖片描述

這裏寫圖片描述

源代碼下載

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章