Java POI 讀寫Excel 檔案簡單實現
阿新 • • 發佈:2019-01-03
整理FileUtils的一些方法,只是一些初步實現,剛寫完就掛上來了…
友情提示:**過於結構化,沒太多潤色....碼的不好還請諸位海涵並多提意見**
關聯的型別
資源 | 型別 | 說明 |
---|---|---|
Workbook | 介面 | Excel工作簿的高階表示。這是大多數使用者在閱讀或編寫工作簿時所構建的第一個物件。它也是建立新表/等的頂級物件 |
WorkbookFactory | 類 | 建立合適的工作簿(HSSFWorkbook或XSSFWorkbook),從提供的輸入中自動檢測。 |
HSSFWorkbook | 類 | .xls (97版和2003版的格式) |
XSSFWorkbook | 類 | .xlsx (2007之後版本格式) |
Sheet | 介面 | Excel工作表的高階表示。表是工作簿中的中心結構,並且是使用者在其電子表格中工作的地方。最常見的表型別是工作表,它表示為單元格網格。工作表單元格可以包含文字、數字、日期和公式。單元格也可以被格式化。 |
Row | 介面 | 行 |
Cell | 介面 | 單元格 |
jar包預覽:
概述
- 讀取:
利用WorkbookFactory 構建一個Workbook物件,按次生成Sheet[1…255]03版,[1…n]07版.根據資料來源容器(size)建立對應行(row)的個數rowNumber = size+1(保留一個title),可以理解為一個row代表一個Object,而對應行(row)所包含的單元格(Cell)就是Object的成員屬性. - 寫入:
與讀取方法不同的事,寫入根據實際需求決定是哪種檔案格式,另外Cell.setCellStyle()可以定義單元格的外觀,換句話說,寫入的時候如果將寫入的資料只是作為一般儲存,也沒必要糾結於樣式. - Excel 提供的6中引數型別:
Tag | 說明 |
---|---|
Cell.CELL_TYPE_STRING | 代表文字 |
Cell.CELL_TYPE_BLANK | 空白格 |
Cell.CELL_TYPE_BOOLEAN: | 布林型 |
Cell.CELL_TYPE_NUMERIC | 數字 |
Cell.CELL_TYPE_ERROR | 錯誤 |
Cell.CELL_TYPE_FORMULA | 公式 |
程式碼部分
讀取Excel檔案
public static <T> Map<String, List<? extends T>> readExcel(String path, Class clzz) {
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
List<T> list = new LinkedList<T>();
Map<String, List<? extends T>> map = new HashMap<String, List<? extends T>>();
File file = new File(path);
FileInputStream fis = null;
Workbook workBook = null;
if (file.exists()) {
try {
fis = new FileInputStream(file);
workBook = WorkbookFactory.create(fis);
int numberOfSheets = workBook.getNumberOfSheets();
for (int s = 0; s < numberOfSheets; s++) { // sheet工作表
Sheet sheetAt = workBook.getSheetAt(s);
// String sheetName = sheetAt.getSheetName(); //獲取工作表名稱
int rowsOfSheet = sheetAt.getPhysicalNumberOfRows(); // 獲取當前Sheet的總列數
System.out.println("當前表格的總行數:" + rowsOfSheet);
for (int r = 0; r < rowsOfSheet; r++) { // 總行
Row row = sheetAt.getRow(r);
if (row == null) {
continue;
} else {
int rowNum = row.getRowNum();
System.out.println("當前行:" + rowNum);
int numberOfCells = row.getPhysicalNumberOfCells();
for (int c = 0; c < numberOfCells; c++) { // 總列(格)
Cell cell = row.getCell(c);
if (cell == null) {
continue;
} else {
int cellType = cell.getCellType();
switch (cellType) {
case Cell.CELL_TYPE_STRING: // 代表文字
String stringCellValue = cell.getStringCellValue();
System.out.print(stringCellValue + "\t");
break;
case Cell.CELL_TYPE_BLANK: // 空白格
String stringCellBlankValue = cell.getStringCellValue();
System.out.print(stringCellBlankValue + "\t");
break;
case Cell.CELL_TYPE_BOOLEAN: // 布林型
boolean booleanCellValue = cell.getBooleanCellValue();
System.out.print(booleanCellValue + "\t");
break;
case Cell.CELL_TYPE_NUMERIC: // 數字||日期
boolean cellDateFormatted = DateUtil.isCellDateFormatted(cell);
if (cellDateFormatted) {
Date dateCellValue = cell.getDateCellValue();
System.out.print(sdf.format(dateCellValue) + "\t");
} else {
double numericCellValue = cell.getNumericCellValue();
System.out.print(numericCellValue + "\t");
}
break;
case Cell.CELL_TYPE_ERROR: // 錯誤
byte errorCellValue = cell.getErrorCellValue();
System.out.print(errorCellValue + "\t");
break;
case Cell.CELL_TYPE_FORMULA: // 公式
int cachedFormulaResultType = cell.getCachedFormulaResultType();
System.out.print(cachedFormulaResultType + "\t");
break;
}
}
}
System.out.println(" \t ");
}
System.out.println("");
}
}
if (fis != null) {
fis.close();
}
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
} else {
System.out.println("檔案不存在!");
}
return map;
}
寫入Excel
@SuppressWarnings("resource")
public static <T> void writeExcel(String path, List<T> list, Class<T> clzz) {
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
Field[] declaredFields = clzz.getDeclaredFields();
File file = new File(path);
FileOutputStream fos = null;
Workbook workbook = null;
try {
if (file.exists()) {
fos = new FileOutputStream(file);
String suffix = getSuffix(path);
if (suffix.equalsIgnoreCase("XLSX")) {
workbook = new XSSFWorkbook();
} else if (suffix.equalsIgnoreCase("XLS")) {
workbook = new HSSFWorkbook();
} else {
throw new Exception("當前檔案不是excel檔案");
}
Sheet sheet = workbook.createSheet(); // 生成工作表
Row row = sheet.createRow(0);
for (int m = 0; m < declaredFields.length; m++) { // 設定title
Field field = declaredFields[m];
field.setAccessible(true);
Cell cell = row.createCell(m);
String name = field.getName();
cell.setCellType(Cell.CELL_TYPE_STRING);
cell.setCellValue(name);
}
for (int i = 0; i < list.size(); i++) { // 資料
T instance = list.get(i);
row = sheet.createRow(i + 1);
for (int j = 0; j < declaredFields.length; j++) {
Field field = declaredFields[j];
Object value = field.get(instance);
String fieldTypeName = field.getGenericType().getTypeName();
field.setAccessible(true);
Cell cell = row.createCell(j);
switch (fieldTypeName) {// content
case "long":
double d = Double.valueOf(value.toString());
cell.setCellValue(d);
break;
case "float":
CellStyle floatStyle = workbook.createCellStyle();
short format = workbook.createDataFormat().getFormat(".00");// 保留2位精度
floatStyle.setDataFormat(format);
double d1 = Double.parseDouble(String.valueOf(value));
cell.setCellStyle(floatStyle);
cell.setCellValue(d1);
break;
case "int":
double d2 = Double.parseDouble(String.valueOf(value));
cell.setCellValue(d2);
break;
case "java.util.Date":
CellStyle dateStyle = workbook.createCellStyle();
short df = workbook.createDataFormat().getFormat("yyyy-mm-dd");
dateStyle.setDataFormat(df);
cell.setCellStyle(dateStyle);
String format2 = sdf.format(value);
Date date = sdf.parse(format2);
cell.setCellValue(date);
break;
case "java.lang.String":
cell.setCellValue(value.toString());
break;
}
}
workbook.write(fos);
}
} else {
if (file.createNewFile()) {
writeExcel(path, list, clzz);
} else {
System.out.println("建立Excel表格失敗!");
}
}
if (fos != null) {
fos.close();
}
} catch (Exception e) {
e.printStackTrace();
}
}
擷取檔案字尾
public static String getSuffix(String path) {
String substring = path.substring(path.lastIndexOf(".") + 1);
return substring;
}
初步實現大概就是這樣,還有很多不完善的地方:
- 比如資料型別對應(本人用的校驗不完善);
- 還有就是讀寫效率與效能優化;
- 資料同步,避免髒讀髒寫;
- 其它的以後補充…