这几天做excel导入数据.刚开始使用jxl导入03版的,因为数据量超过65536,03版装不下,所以就用poi来支持07版的.
直接网上copy了个代码过去,搞了2条数据测试下成功了.
结果在导入正式数据的时候,才20M的excel文件就内存溢出了.网上搜了下,这情况很常见,需要使用sax方式来解析才可以.
但是在使用中,历经磨难,所以记录下来,以增强记忆.
还有好几个问题没解决,也一起记录下来,看哪位帮忙解决.
代码总共三段. 1.解析.2.抽象接口.3.业务类
1.解析类,继承DefaultHandler
/**
* 抽象Excel2007读取器,excel2007的底层数据结构是xml文件,采用SAX的事件驱动的方法解析
* xml,需要继承DefaultHandler,在遇到文件内容时,事件会触发,这种做法可以大大降低
* 内存的耗费,特别使用于大数据量的文件。
*
*/
public class Excel2007Reader extends DefaultHandler {
//共享字符串表
private SharedStringsTable sst;
//上一次的内容
private String lastContents;
private boolean nextIsString;
private int sheetIndex = -1;
private List<String> rowlist = new ArrayList<String>();
//当前行
private int curRow = 0;
//当前列
private int curCol = 0;
// 当前遍历的Excel单元格列索引
protected int thisColumnIndex = -1;
private String defaultStr = "";
private boolean listIsNull = true;
protected int total = 0; //总行数
private int totalCol = 0;//总列数
private String sheetName;
private IRowReader rowReader;
public void setRowReader(IRowReader rowReader){
this.rowReader = rowReader;
}
/**
* 根据sheetid 解析sheet
* @param stream
* @param sheetId
* @throws Exception
*/
public void processOneSheetByIndex(String filename,int sheetId) throws Exception {
OPCPackage pkg = OPCPackage.open(filename);
XSSFReader r = new XSSFReader(pkg);
SharedStringsTable sst = r.getSharedStringsTable();
XMLReader parser = fetchSheetParser(sst);
// 根据 rId# 查找sheet
InputStream sheet2 = r.getSheet("rId"+sheetId);
sheetIndex++;
InputSource sheetSource = new InputSource(sheet2);
parser.parse(sheetSource);
sheet2.close();
}
/**
* 根据sheet名称,解析sheet
* @param stream
* @param name
* @throws Exception
*/
public void process(InputStream stream) throws