归纳POI对EXCEL2007版本及以上的常见操作

通过指定列头集合创建EXCEL模板(初始化EXCEL模板为文本格式)

 /**
     * 根据列头创建Excel模板
     *
     * @param headList
     * @return
     */
    public static XSSFWorkbook createWorkBook(List headList) {
        XSSFWorkbook wb = new XSSFWorkbook();
        XSSFSheet sheet = wb.createSheet("数据表");
        //设置excel为文本格式
        XSSFCellStyle cellStyle = wb.createCellStyle();
        XSSFDataFormat dataFormat = wb.createDataFormat();
        cellStyle.setDataFormat(dataFormat.getFormat("@"));
        for(int column=0;column<=headList.size();column++){
            sheet.setDefaultColumnStyle(column,cellStyle);
        }
        buildHeader(sheet, headList);
        return wb;
    }
/**
 * 创建表头
 *
 * @param sheet
 */
private static void buildHeader(XSSFSheet sheet, List headList) {
    XSSFRow headerRow = sheet.createRow(0);
    int index = 0;
    for (String header : headList) {
        XSSFCell cell = headerRow.createCell(index, Cell.CELL_TYPE_STRING);
        cell.setCellValue(header);
        index++;
    }
}

获取当前单元格内容

   /**
     * 获取当前单元格内容
     */
    public static String getCellValue(Cell cell) {
        String value = "";
        if(cell!=null){
            cell.setCellType(Cell.CELL_TYPE_STRING);
            value = cell.getStringCellValue();
        }
        return value;
    }

判断某一行的所有单个格是否有值

  /**
     * 判断某一行的所有单个格是否有值
     *
     * @param row 当前行
     * @param cells 当前行总列数
     * @return
     */
    private static boolean isThereAValue(XSSFRow row, int cells) {
        for (int i = 0; i < cells; i++) {
            XSSFCell rowcell = row.getCell(i);
            String cellValue = ExcelUtils.getCellValue(rowcell);
            if (null != cellValue && !"".equals(cellValue)) {
                return true;
            }
        }
        return false;
    }

获取EXCEL中不为空行的行数

 /**
     * 获取excel的不为空的行数
     *
     * @param sheet
     * @param lastRows sheet对应最后一行的编号
     * @return
     */
public static int getExcelRows(XSSFSheet sheet, int lastRows) {
    boolean isThereAValue;
    int rows = 0;
    for (int i = 0; i <=lastRows; i++) {
        XSSFRow row = sheet.getRow(i);
        if (row == null) {
            continue;
        }
        int cells = sheet.getRow(0).getLastCellNum();
        isThereAValue = ExcelUtils.isThereAValue(row, cells);
        if (!isThereAValue) {
            continue;
        }
        rows++;
    }
    return rows;
}

获取第一栏标题栏数据

 /**
     * 获取第一行标题栏数据
     *
     * @param sheet
     * @return map key:标题栏列下标(0开始) value 标题栏值
     * @throws ExportException
     */
    private static Map loadHeader(XSSFSheet sheet) {
        Map header = new HashMap();
        int HEADER = 0;
        XSSFRow row = sheet.getRow(HEADER);
        int columns = row.getLastCellNum();
        for (int i = 0; i < columns; i++) {
            log.info("加载标题栏:" + row.getCell(i).getStringCellValue());
            String value = row.getCell(i).getStringCellValue();
            if (null == value) {
                throw new RuntimeException("标题栏不能为空!");
            }
            header.put(i, value);
        }
        return header;
    }

解析EXCEL模板将Workbook中的值放入List>结构中

 /**
     * 将workbook中的值放入List>结构中
     *
     * @param workbook
     * @return
     */
    public static List> parseExcel(Workbook workbook) {
        log.info("开始解析excel");
        List> result = new LinkedList>();
        //获取第一个sheet
        XSSFSheet sheet = (XSSFSheet) workbook.getSheetAt(0);
        if (sheet == null || sheet.getRow(0) == null) {
            return result;
        }
        int physicalNumberOfRows = sheet.getPhysicalNumberOfRows();
        log.info("解析excel的物理行数" + physicalNumberOfRows);
        int rows=getExcelRows(sheet,sheet.getLastRowNum());
        log.info("解析excel的有效行数" + rows);
        //获取标题行的总列数
        int excleRowLength = sheet.getRow(0).getLastCellNum();
        //相应的javabean类的属性名称数组
        String[] columnName = new String[excleRowLength];
        //获取第一栏标题栏数据
        Map header = loadHeader((XSSFSheet) workbook.getSheetAt(0));
        for (int i = 0; i < columnName.length; i++) {
            columnName[i] = header.get(i);
        }
        for (int rowIndex = 1; rowIndex <= sheet.getLastRowNum(); rowIndex++) {
            XSSFRow row = sheet.getRow(rowIndex);
            if (row == null || !isThereAValue(row,sheet.getRow(0).getLastCellNum())) {
                continue;
            }
            Map map = new HashMap();
            for (int cellIndex = 0; cellIndex < columnName.length; cellIndex++) {
                XSSFCell cell = row.getCell(cellIndex);
                //该列值在对应的java对象中有值
                if (columnName[cellIndex] != null && columnName[cellIndex].trim().length() > 0) {
                    //取出当前cell的值和对应Javabean类的属性放入到map中
                    map.put(columnName[cellIndex].trim(), getCellValue(cell));
                }
            }
            result.add(map);
        }
        return result;
    }

POI操作EXCEL常见问题

  • sheet.getLastRowNum()与sheet.getPhysicalNumberOfRows()的区别?
    getPhysicalNumberOfRows:获取的是物理行数也就是不包括那些空行或隔行的情况,包括清空某行的情况,用于判读excel的有效物理行数。
    getLastRowNum:获取的是最后一行的编号(编号从0开始),用于遍历获取EXCEL每行内容,常见用法for (int rowIndex = 1; rowIndex <= lastRowNum; rowIndex++)。
  • XSSFRow.getLastCellNum()与XSSFRow.getPhysicalNumberOfCells()区别?
    getPhysicalNumberOfCells: 是获取不为空的列个数
    getLastCellNum: 是获取最后一个不为空的列是第几个(编号从1开始,若是excel数据中存在空列,必须用getLastCellNum才能完全读取数据)。
  • 获取当前单元格内容因为单元格格式的不同,导致后端获取的内容与单元格实际内容有差异?
    方案一:控制导入的EXCEL模板为文本格式,后端同时采用获取字符串的方式获取单元格内容。

你可能感兴趣的:(poi-excel)