环境:jdk 1.5
分批读取,还是溢出,求解
注:不要用事件模式,不要调整内存
附上代码
package ttt;import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.InputStream;
import java.util.ArrayList;import org.apache.poi.xssf.usermodel.XSSFCell;
import org.apache.poi.xssf.usermodel.XSSFRow;
import org.apache.poi.xssf.usermodel.XSSFSheet;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;
/**
 * 分批读取提交
 *
 */
public class TT4 {
XSSFSheet xssfSheet =null;//Sheet 对象
ArrayList<ArrayList<String>> ans = new ArrayList<ArrayList<String>>();
ArrayList<ArrayList<String>> arr = null;

/**
 * 初始化Sheet
 */
public TT4(){
XSSFWorkbook xssfWorkbook = null;
File excelFile = new File("D:\\work\\workWord\\资料\\案例\\","template.xlsx");
InputStream is;
try {
is = new FileInputStream(excelFile);
xssfWorkbook = new XSSFWorkbook(is);
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
xssfSheet = xssfWorkbook.getSheetAt(0);
}

public static void main(String[] args) throws IOException {
new TT4().test();


}

/**
 * 分批测试
 * @throws IOException
 */
public void test() throws IOException{
int lastRowNum = xssfSheet.getLastRowNum();
int excecuteNum = this.testRowNumber(lastRowNum);

for(int i = 0 ;i < excecuteNum; i++){
switch (i){
case 1:
this.printOut(3,1000);
break;
case 2:
this.printOut(1001,2000);
break;
case 3:
this.printOut(2001,3000);
break;
case 4:
this.printOut(3001,4000);
break;
case 5:
this.printOut(4001,5000);
break;
case 6:
this.printOut(5001,6000);
break;
}
}
}


/**
 * 打印输出
 * @param beginRow
 * @param endRow
 * @throws IOException
 */
public void printOut(int beginRow,int endRow) throws IOException{
arr=this.xlsx_reader(0,beginRow,endRow,0,8);
ArrayList<String> row = null;
for(int i=0;i<arr.size();i++){
 row=arr.get(i);
for(int j=0;j<row.size();j++){
System.out.print(row.get(j)+" ");
}
System.out.println("");
}
ans.clear();
arr.clear();
} /**xlsx文件读取函数
 * @param sheetNumArg 第几个Sheet
 * @param rowNumBegin 开始行
 * @param rowNumEnd 结束行
 * @param columnBegin 开始列
 * @param columnEnd 结束列
 * @return
 * @throws IOException
 */
public ArrayList<ArrayList<String>> xlsx_reader(int sheetNumArg,
int rowNumBegin, int rowNumEnd, int columnBegin, int columnEnd)
throws IOException { if (xssfSheet == null) {
return null;
} // 对于每个sheet,读取其中的每一行
for (int rowNum = rowNumBegin; rowNum <= rowNumEnd; rowNum++) {
XSSFRow xssfRow = xssfSheet.getRow(rowNum);
if (xssfRow == null) {
continue;
}
ArrayList<String> curarr = new ArrayList<String>();
for (int columnNum = columnBegin; columnNum < columnEnd; columnNum++) {
XSSFCell cell = xssfRow.getCell(columnNum);
curarr.add(Trim_str(getValue(cell)));
}
ans.add(curarr);
curarr = null;
}
return ans;
}
    
    //判断后缀为xlsx的excel文件的数据类
    @SuppressWarnings({"static-access" })
private static String getValue(XSSFCell xssfRow) {
     if(xssfRow==null){
     return "";
     }
        if (xssfRow.getCellType() == xssfRow.CELL_TYPE_BOOLEAN) {
            return String.valueOf(xssfRow.getBooleanCellValue());
            
        } else if (xssfRow.getCellType() == xssfRow.CELL_TYPE_NUMERIC) {
         double cur=xssfRow.getNumericCellValue();
         long longVal = Math.round(cur);
         Object inputValue = null;
         if(Double.parseDouble(longVal + ".0") == cur)  
                 inputValue = longVal;  
         else  
                 inputValue = cur; 
            return String.valueOf(inputValue);
            
        } else if(xssfRow.getCellType() == xssfRow.CELL_TYPE_BLANK || xssfRow.getCellType() == xssfRow.CELL_TYPE_ERROR){
         return "";
        }
        
        else {
            return String.valueOf(xssfRow.getStringCellValue());
        }
    }
    
    
  //字符串修剪  去除所有空白符号 , 问号 , 中文空格
static private String Trim_str(String str) {
if (str == null)
return null;
return str.replaceAll("[\\s\\?]", "").replace(" ", "");
}

/**
 * 根据总行数,判断读几次
 * 一千行一次
 */
public int testRowNumber(int i){
if(0 == i){
return 0;
}
if(i<1000){
return 1;
}else{
return i / 1000 +1;
}
}}

解决方案 »

  1.   

    参照
    http://www.cnblogs.com/resentment/p/6367404.html
      

  2.   

    在你分批前就已经溢出了,所以不要费力气在分批上,把excel拆成小的或者采用流方式读取。
      

  3.   

    谢谢回答!
    附的代码是POI的用户模式读取的,你说的哪个应该就是事件模式的,事件模式速度非常快,也不会溢出,但是它读数据的时候会忽略掉空的单元格,直接跳到下个有值的单元格
      

  4.   

    谢谢回答!
    附的代码是POI的用户模式读取的,你说的哪个应该就是事件模式的,事件模式速度非常快,也不会溢出,但是它读数据的时候会忽略掉空的单元格,直接跳到下个有值的单元格
    我不能重现你的问题,所以只能试着给你方案。
    1.ans和arr都是类变量,变成局部变量试一下。
    2.我看到你用的list.clear方法来释放存储空间,没有仔细研究,如果list本身本撑大到一定程度的话,clear是否能迅速释放空间?还是每次new一个list在局部变量,方法栈退出后自然没有引用。
      

  5.   

    文件太大就用csv 了