2013-03-26 84 views
0

我有一个下面提到的java类,它提取一个zip,并逐个将其内容转换为字符串并打印到控制台。
问题是,当zip内的文件大〜80KB时。整个内容没有被显示(只有3/4的数据被转换为字符串并在控制台中显示)。
其次,下面提到的代码是在介于两者之间的空/空间以及如果文件大小很小〜1KB无法使用ZipInputStream处理zip文件中的大文件

下面提到的代码中出现了什么问题。

public static void main(String[] args) throws Exception { 
    byte[] buf = new byte[1024]; 
    final int BUFFER = 1024; 
    String fName = "c:\\DOC00001.zip"; 
    ZipInputStream zinstream = new ZipInputStream(
      new FileInputStream(fName)); 
    ZipEntry zentry = zinstream.getNextEntry(); 

    while (zentry != null) {    
    byte data[] = new byte[BUFFER]; 
    ByteArrayOutputStream out = new ByteArrayOutputStream(); 
    while ((zinstream.read(data, 0, BUFFER)) != -1) { 
     out.write(data); 
    }  
    InputStream is = new ByteArrayInputStream(out.toByteArray()); 
    StringWriter writer = new StringWriter(); 
    IOUtils.copy(is, writer, "UTF-8"); 
    String response = writer.toString(); 
    System.out.println(response); 
    zentry = zinstream.getNextEntry(); 
    } 
    zinstream.close(); 
} 

回答

0

read方法不能保证读缓冲区满;返回已读取的字节数。提取从一个zip文件,或任何一般InputStream数据的正确方法,是:

byte[] data = new byte[BUFFER]; 
ByteArrayOutputStream out = new ByteArrayOutputStream(); 
int bytesRead; 
while ((bytesRead = zinstream.read(data, 0, BUFFER)) != -1) { 
    out.write(data, 0, bytesRead); 
} 

或者,因为你已经在使用IOUtils

ByteArrayOutputStream out = new ByteArrayOutputStream(); 
IOUtils.copy(zinstream, out); 

或者,因为你写一个ByteArrayOutputStream只能稍后写入一个字符串,您可以完全跳过ByteArrayOutputStream

while (zentry != null) { 
    StringWriter writer = new StringWriter(); 
    IOUtils.copy(zinstream, writer, "UTF-8"); 
    String response = writer.toString(); 
    System.out.println(response); 
    zentry = zinstream.getNextEntry(); 
}