POI读取单元格信息及单元格公式
Java操作EXCEL的利器一般都是POI和JXL,鄙人只是POI的忠实粉丝。(其实我是没有用过JXL)。
现在大多数的excel都是07以上的版本,所以我一般是用07的基础上使用POI。
- 一、读取单元格
单元格有样式和值,以及值得类型。
样式复制封装成一个函数:
public XSSFCellStyle cloneAllCellStyle(XSSFCell sourceCell, XSSFWorkbook targetWb){ //创建一个样式 XSSFCellStyle tempStyle = targetWb.createCellStyle(); //样式 //数值格式,创建字符及数字格式 DataFormat format= targetWb.createDataFormat(); //字体 XSSFFont font= targetWb.createFont(); try{ tempStyle.setDataFormat(format.getFormat( sourceCell.getCellStyle().getDataFormatString())); }catch(NullPointerException e){ tempStyle.setDataFormat((short)0); } font.setColor(sourceCell.getCellStyle().getFont().getXSSFColor()); font.setBold(sourceCell.getCellStyle().getFont().getBold()); font.setBoldweight(sourceCell.getCellStyle().getFont().getBoldweight()); try{ font.setCharSet(sourceCell.getCellStyle().getFont().getCharSet()); }catch(POIXMLException e){ font.setCharSet(0); } // font.setCharSet(sourceCell.getCellStyle().getFont().getCharSet()); font.setFamily(sourceCell.getCellStyle().getFont().getFamily()); font.setFontHeight(sourceCell.getCellStyle().getFont().getFontHeight()); font.setFontHeightInPoints(sourceCell.getCellStyle().getFont().getFontHeightInPoints()); font.setFontName(sourceCell.getCellStyle().getFont().getFontName()); font.setItalic(sourceCell.getCellStyle().getFont().getItalic()); font.setStrikeout(sourceCell.getCellStyle().getFont().getStrikeout()); // font.setThemeColor(sourceCell.getCellStyle().getFont().getThemeColor()); font.setTypeOffset(sourceCell.getCellStyle().getFont().getTypeOffset()); font.setUnderline(sourceCell.getCellStyle().getFont().getUnderline()); tempStyle.setAlignment( sourceCell.getCellStyle().getAlignment()); tempStyle.setVerticalAlignment(sourceCell.getCellStyle().getVerticalAlignment()); tempStyle.setBorderBottom(sourceCell.getCellStyle().getBorderBottom()); tempStyle.setBorderLeft(sourceCell.getCellStyle().getBorderLeft()); tempStyle.setBorderRight(sourceCell.getCellStyle().getBorderRight()); tempStyle.setBorderTop(sourceCell.getCellStyle().getBorderTop()); tempStyle.setBottomBorderColor(sourceCell.getCellStyle().getBottomBorderXSSFColor()); tempStyle.setLeftBorderColor(sourceCell.getCellStyle().getLeftBorderXSSFColor()); tempStyle.setRightBorderColor(sourceCell.getCellStyle().getRightBorderXSSFColor()); tempStyle.setTopBorderColor(sourceCell.getCellStyle().getTopBorderXSSFColor()); tempStyle.setFillBackgroundColor(sourceCell.getCellStyle().getFillBackgroundColorColor()); tempStyle.setFont(font); try{ tempStyle.setFillForegroundColor(sourceCell.getCellStyle().getFillForegroundColorColor()); }catch(NullPointerException e){ tempStyle.setFillForegroundColor(IndexedColors.WHITE.getIndex()); } tempStyle.setFillPattern(sourceCell.getCellStyle().getFillPattern()); tempStyle.setRotation(sourceCell.getCellStyle().getRotation()); tempStyle.setHidden(sourceCell.getCellStyle().getHidden()); tempStyle.setWrapText(sourceCell.getCellStyle().getWrapText()); tempStyle.setIndention(sourceCell.getCellStyle().getIndention()); tempStyle.setLocked(sourceCell.getCellStyle().getLocked()); return tempStyle; }
调用直接获取单元格的样式内容。
获取单元格值的类型:cell.getCellType()
根据值类型不同获取不同的值:
switch (cell.getCellType()) { case Cell.CELL_TYPE_BLANK: tempValue.add(""); break; case Cell.CELL_TYPE_BOOLEAN: tempValue.add(cell.getBooleanCellValue()); break; case Cell.CELL_TYPE_ERROR: tempValue.add(cell.getErrorCellString()); break; case Cell.CELL_TYPE_FORMULA: tempValue.add(cell.getCellFormula()); map.put("formulaFlag", true); break; case Cell.CELL_TYPE_NUMERIC: tempValue.add(cell.getNumericCellValue()); break; case Cell.CELL_TYPE_STRING: tempValue.add(cell.getStringCellValue()); break; default: break; }
创建内容
//工作空间 XSSFWorkbook targetWb = new XSSFWorkbook(); //sheet XSSFSheet targetSheet = targetWb.createSheet("行汇总"); // 删除sheet targetWb.removeSheetAt(index); //index表示第几个sheet,从0开始计数 //row XSSFRow row=targetSheet.createRow(i+num1-startRow+1); //cell XSSFCell cell=row.createCell(j); //j 行
二、 操作单元格函数
POI能够读取函数,然后再把函数写入到单元格中,excel自己计算函数。而函数操作单元格的位置,一般是固定的,所以操作的单元格无法改变。
1、读取函数和写入函数
cell.getCellFormula()
上面的代码中,获取函数的内容,类型为string。
写入函数:
cell.setCellFormula((String)cellValues.get(j));
2、获取函数计算之后的值:
有的地方直接写:
cell.getNumberValue();这样有时候会报错,当cell的内容不是值得时候。
最后做一个异常抛出。
当然有时候也读不出值,读出的值是0.0(double)
读取函数值得另一种方法:
XSSFFormulaEvaluator evaluator=new XSSFFormulaEvaluator(targetWb); CellValue tempCellValue = evaluator.evaluate(cell); double cellValue1 = tempCellValue.getNumberValue();
如何你是获取excel的值之后,再写入另一个单元格,建议写入值之前,先改变单元的值类型,变成数值型:
cell.set(XSSFCell.CELL_TYPE_NUMERIC);