java通過POI技術操作Excel(2)----模板讀取,錄入數據


  先來回顧下通常把java對Excel的操作分為以下功能:1、生成模板,導出模板;2、填充模板,錄入數據;3;讀取數據庫數據,導出數據;在上一篇博文中,我簡單記錄了模板生成和導出,在這篇博文中,主要來記錄--Excel文件導入,數據錄入(仍然是以jsp+servlet為例)

  既然要解決這個問題,那首先來分析下我們需要面對的有哪些需求需要實現:

  1、Excel文件導入(這是最基礎的,巧婦難為無米之炊,導入環節也是查了好久才完成的);

  2、Excel文件中數據的格式判定,你要讀取文件,如果文件中其實沒有數據怎么辦,程序會報錯么;

  3、Excel文件中數據的數值判定,“編號”啊,“身份證號”啊之類是不是需要有一定的規范才說明數值是正確的,否則錄入毫無意義,數據庫中可能還會報錯;

  4、Excel文件中數據判定完成后,判定全部正確的,全部錄入數據庫,錄入成功顯示錄入成功,錄入不成功則修改錄入環節;

                 判定如果存在錯誤,將所有出現錯誤的列匯總,返回界面提示所有出錯的列;

 首先,我們來完成導入功能,實現如下效果:

相信這個上傳效果,很多人都能實現,<input type="file">如是而已嘛,但是實現它后我們如何進行excel數據操作呢?通常我們想到的有如下兩種方法:

1、將excel文件傳上去,然后對傳上的文件進行操作,因為我們傳到哪了我們知道,可以直接獲取路徑;

2、我們可以直接獲取想要上傳的文件在電腦上的路徑,然后我們通過路徑直接對文件進行操作;

這里我主要來介紹下我實現的第二種方法,(以ie瀏覽器為例,其它瀏覽器暫不討論)

 1 function upLoad(){
 2     var myFile=document.getElementById("myFile");
 3     myFile.select();
 4     var realPath=document.selection.createRange().text;
 5     var len=realPath.length;
 6     var path=realPath.substr(len-4);
 7     if(path==".xls"){       
      document.getElementById("myForm").action="upLoad?path="+realPath; 8   document.getElementById("myForm").submit(); 9 }else{ 10 alert("請輸入excel格式的文件"); 11 } 12 }

通常情況下,在ie7之前我們可以通過document.getElementById('file_upl').value 直接獲取文本的本地路徑,但是在ie8之后,處於安全性考慮,上傳時獲取以上value值則會以“C:\fakepath\”來代替了,這個時候我們就需要 上文中出現的var myFile=document.getElementById("myFile"); myFile.select();var realPath=document.selection.createRange().text;這三步來進行完成了。

這樣在ie瀏覽器下就可以獲取到文件的本地路徑了,從而繼續接下來的文本讀取工作。

其次,我們來解決接下來的問題,既然找到文件了,那就開始對文件進行操作,

 (這里我們只考慮,對某個單個文件的直接讀取,不考慮多文件優化等問題)我們通過如下步驟來進行數據讀取:

a、java對excel的數據讀取,原理上是將excel上的數據復制到hssfworkbook工作簿上,然后對工作簿進行操作

1 File file=new FileInputStream(String path)
2 BufferedInputStream bis=new BufferedInputStream(file);
3 POIFSFileSystem pfs=new POIFSFileSystem(bis);

b、復制完成后就是對hssfworkbook工作簿上數據的處理,是從頁、行、列依次進行開始讀取

 1 //每一頁每一頁的進行數據處理
 2 HSSFWorkbook book=new HSSFWorkbook(pfs);
 3 for (int k = 0; k < book.getNumberOfSheets(); k++) {
 4     HSSFSheet sheet=book.createSheet();
 5     //每一行每一行的進行處理
 6     for (int i = 0; i < sheet.getLastRowNum(); i++) {
 7         HSSFRow row=sheet.createRow(i);
 8         if(row==null){continue;}
 9         String[] values = new String[i];
10         Arrays.fill(values, "");
11         for (int j = 0; j < row.getLastCellNum()+1; j++) {
12         String value="";
13         HSSFCell cell=row.createCell(j);

c、在進行每一個單元格讀取的時候,我們需要根據不同的數據,用不同的獲取方法,避免讀取過程出現異常

 1 switch (cell.getCellType()) {
 2 case HSSFCell.CELL_TYPE_STRING:
 3      value = cell.getStringCellValue();
 4 break;
 5 case HSSFCell.CELL_TYPE_NUMERIC:
 6     if (HSSFDateUtil.isCellDateFormatted(cell)) {
 7         Date date = cell.getDateCellValue();
 8     if (date != null) {
 9     value = new SimpleDateFormat("yyyy-MM-dd").format(date);
10     } else {
11         value = "";
12     }
13     } else {
14     value = newDecimalFormat("0").format(cell.getNumericCellValue());
15 }
16 break;
17 case HSSFCell.CELL_TYPE_FORMULA:
18     // 導入時如果為公式生成的數據則無值
19     if (!cell.getStringCellValue().equals("")) {
20         value = cell.getStringCellValue();
21     } else {
22         value = cell.getNumericCellValue() + "";
23     }
24 break;
25 case HSSFCell.CELL_TYPE_BLANK:
26         value="";
27 break;
28 case HSSFCell.CELL_TYPE_ERROR:
29         value = "";
30 break;
31 case HSSFCell.CELL_TYPE_BOOLEAN:
32         value = (cell.getBooleanCellValue() == true ? "Y":"N");
33 break;
34 default:
35     value = "";
36 }        

如上是對不同數據類型不同的讀取,java的poi讀取中,通常用到的數據類型為:

CELL_TYPE_BLANK 空值
CELL_TYPE_BOOLEAN 布爾型
CELL_TYPE_ERROR 錯誤
CELL_TYPE_FORMULA 公式型
CELL_TYPE_STRING 字符串型
CELL_TYPE_NUMERIC 數值型

d、接下來就是對於不同的數據判定結果,進行的操作不同,在這里我們判定如果正確列直接錄入數據庫,如果不正確的則返回界面

(當然實際應用中應當是全部正確才能錄入,如果存在不正確的數據,整個文件都不能錄入)

 1 if (i == 0 && value.trim().equals("")) {
 2 break;
 3 }
 4     values[i] = value;
 5 }
 6 }
 7 }
 8 }
 9 //進行判定全局變量boolean值all,如果為true,則說明已經數據完全正確,則取值向數據庫中進行存取,如果為false則存在錯誤信息,將得到的錯誤信息直接返回,不再向數據庫發送存取請求            
10 }
11 return returnArray;
12 }

最后面這部分寫的略微有些凌亂,這樣我們來回顧一下讀取步驟:

1、獲取文件地址;

2、根據文件地址,讀取文件;

(這里應該是讀取全部數據,可以先進行基本數據的判定,如果存在不對的數據類型,則記錄並返回提示,如果正確了再進行下一步);

3、如果判定之前的數據類型設定都正確了,則進行判定數據的具體規格,例如:編號前幾位必須為http,身份證號碼共18位等;

4、如果以上所有的判定都滿足,則將數據進行錄入數據庫操作,(數據錄入數據庫,相信都不會陌生了吧)

  如果存在問題,則應該返回界面進行相應的提示操作。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM