poi 匯入Excel封裝 並處理資料型別
阿新 • • 發佈:2019-02-04
最近正在做OA,需求需要匯入匯出EXCEL ,功能和方法使用起來挺簡單,做起來發現型別問題比較坑,自己稍微封裝了一下,
大致功能就是 通過傳入實體類的class物件和 Sheet 工作簿物件獲取 從Excel檔案中獲取,實體類集合。
excel2003的.xls格式 對應是HSSFCell,而之後的xlsx對應的則是XSSFCell,但是他們都繼承於Cell,所以使用Cell就可以使用兩種格式的excel匯入了
對於不想匯入的欄位
自定義一個註解,在實體類中的屬性上標註,相應的Excel中也不該有該欄位
有一點不好的是:excel中欄位順序需要和實體類中屬性順序一致,且有自定義註解的屬性不應該出現在Excel中
有時間我會對擴充套件性和通用性做進一步封裝和處理
- 這裡 註解名為NoExport 是因為之前寫匯出的時候命名,額 就沒有改了
/**
* 自定義標籤 : 標註了的物件不匯出匯入
* @author huang
*
*/
@Target(ElementType.FIELD)
@Retention(RetentionPolicy.RUNTIME)
public @interface NoExport {
}
@RequestMapping("/XXXXX")
public String includeEmp(MultipartFile multfile ) throws Exception {
try {
//自己封裝的 匯入功能類
ImportExcel ie = new ImportExcel();
POIFSFileSystem fs = new POIFSFileSystem(multfile.getInputStream());
HSSFWorkbook wb = new HSSFWorkbook(fs);
//獲取匯入的員工集合
List<Employee> emplist = new ArrayList<>();
if ( wb.getSheet("Employee表")!=null ) {
emplist = (List <Employee>) ie.getListBySheet(wb.getSheet("Employee表"), Employee.class);
}
List<Department> deplist = new ArrayList<>();
//獲取匯入的職工的集合
if ( wb.getSheet("Department表")!=null ) {
deplist = (List<Department>) ie.getListBySheet(wb.getSheet("Department表"), Department.class);
}
}
匯入功能類
- 方式一:根據實體類的 Field 的型別來判斷處理
- 方式二:根據Cell 型別 判斷處理
- 單元格型別 描述
CELL_TYPE_BLANK 代表空白單元格
CELL_TYPE_BOOLEAN 代表布林單元(true或false)
CELL_TYPE_ERROR 表示在單元的誤差值
CELL_TYPE_FORMULA 表示一個單元格公式的結果
CELL_TYPE_NUMERIC 表示對一個單元的數字資料
CELL_TYPE_STRING 表示對一個單元串(文字)
- 單元格型別 描述
public class ImportExcel {
//通過工作簿 Sheet 獲取物件的List集合
public List<?> getListBySheet( Sheet sheet,Class<?> clas ) {
List<Object> list = new ArrayList<>();
Row rowtitle = sheet.getRow(0);//獲得表頭行
//列數
int colums = rowtitle.getPhysicalNumberOfCells();
//表頭資訊
List<String> title = new ArrayList<>();
for ( int i = 0 ; i < colums ; i++ ) {
title.add( rowtitle.getCell(i).toString() );
}
// 得到總行數
int rows = sheet.getLastRowNum();
for ( int i = 1 ; i <= rows ; i ++ ) {
try {
Row row = sheet.getRow(i);
Object t = clas.newInstance();
Field []fields = clas.getDeclaredFields();
//通過 k 來處理Excel中對應屬性和實體類中的不一致問題
for ( int j=0,k=0; j < fields.length ; j++,k++ ) {
Field field = fields[j];
field.setAccessible(true);
//有 NoExport 註解的 則讓k-- ,保證不會有空列
if ( field.getAnnotation(NoExport.class) !=null ){
k--;
continue;
}
if ( row == null ) {
break;
}
Cell cell = row.getCell(k);
switch (cell.getCellType()) {
//數值型別
case Cell.CELL_TYPE_NUMERIC:{
// Date型別
if ( HSSFDateUtil.isCellDateFormatted(cell) ){
Date date = HSSFDateUtil.getJavaDate(cell.getNumericCellValue());
if ( field.getType()==Date.class ) {//Date 型別接收 Date型別
field.set ( t,date );
}else if ( field.getType()==String.class ) {//String 型別 接收 Date型別
field.set ( t , new SimpleDateFormat("yyyy-MM-dd").parse(cell.getStringCellValue() ) );
}
} else { //純數值
if ( field.getType()==Integer.class ) {//Integer 型別接收 純數值
String str = cell.toString();
//去掉 結尾為.0的情況 正常小數 不會去掉有精度意義的小數
if ( str!=null && !"".equals(str.trim()) ) {
String []strs = str.split("\\.");
if ( strs.length > 1 && "0".equals(strs[1]) ) {
str=strs[0];
}
}
field.set(t, Integer.parseInt(str) ) ;
} else if ( field.getType()==String.class ) { //String 型別接收 純數值
field.set(t, String.valueOf( cell.getNumericCellValue() ) ) ;
}
}
break;
}
// 字串型別
case Cell.CELL_TYPE_STRING : {
if ( field.getType() == Date.class ) { //Data型別接收String
Date date = new SimpleDateFormat("yyyy-MM-dd").parse(cell.getStringCellValue());
field.set(t,date);
} else if ( field.getType()==Integer.class ) { //Integer 型別接收 String
field.set(t,Integer.parseInt(cell.getStringCellValue()));
} else {
field.set(t,cell.getStringCellValue());
}
break;
}
//空值的情況 可以拋異常 也可以 設空值
case Cell.CELL_TYPE_BLANK : {
field.set(t,null);
break;
}
}
//以下 為 以實體類中 屬性為基準
// if ( row.getCell(k)==null ){
// field.set(t, null);
// }else {
// if ( field.getType()==Integer.class ){
// if ( cell.getCellType()==HSSFCell.CELL_TYPE_STRING ) {
// field.set(t, Integer.parseInt( cell.getStringCellValue() ) ) ;
// }
// if ( cell.getCellType()==HSSFCell.CELL_TYPE_NUMERIC ) {
// field.set(t, Integer.valueOf((int) (cell.getNumericCellValue()) )) ;
// }
// }else if ( field.getType()==Date.class ) {
// if ( cell.getCellType()==HSSFCell.CELL_TYPE_NUMERIC ){
// field.set(t, HSSFDateUtil.getJavaDate(cell.getNumericCellValue()));
// }
// if ( cell.getCellType()==HSSFCell.CELL_TYPE_STRING ) {
// field.set(t, new SimpleDateFormat("yyyy-MM-dd").parse(cell.getStringCellValue()) );
// }
// }else {
// String str = cell.toString();
// //去掉 結尾為.0的情況 正常小數 不會去掉有精度意義的小數
// if ( str!=null && !"".equals(str.trim()) ) {
// String []strs = str.split("\\.");
// if ( strs.length > 1 && "0".equals(strs[1]) ) {
// str=strs[0];
// }
// }
// }
// }
}
list.add(t);
} catch (NumberFormatException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (SecurityException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IllegalArgumentException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IllegalAccessException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (InstantiationException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (ParseException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
return list;
}
}