为什么大小是-1?
getNextEntry
在要读取的条目的开头调用ZipInputStream
刚刚定位的读取光标。
大小(连同其他元数据)存储在实际数据的末尾,因此当光标位于开头时不容易获得。
这些信息只有在您阅读整个条目数据或只是转到下一个条目后才可用。
例如,转到下一个条目:
// position at the start of the first entry
entry = zipIn.getNextEntry();
ZipEntry firstEntry = entry;
// size is not yet available
System.out.println("before " + firstEntry.getSize()); // prints -1
// position at the start of the second entry
entry = zipIn.getNextEntry();
// size is now available
System.out.println("after " + firstEntry.getSize()); // prints the size
或读取整个条目数据:
// position at the start of the first entry
entry = zipIn.getNextEntry();
// size is not yet available
System.out.println("before " + entry.getSize()); // prints -1
// read the whole entry data
while(zipIn.read() != -1);
// size is now available
System.out.println("after " + entry.getSize()); // prints the size
您的误解很常见,并且有许多关于此问题的错误报告(已关闭为“不是问题”),例如JDK-4079029、
JDK-4113731、JDK-6491622。
正如错误报告中所提到的,您可以使用whichZipFile
代替ZipInputStream
which 将允许在访问条目数据之前获得大小信息;但是要创建一个ZipFile
,您需要一个File
(请参阅构造函数)而不是字节数组。
例如:
File file = new File( "test.zip" );
ZipFile zipFile = new ZipFile(file);
Enumeration enumeration = zipFile.entries();
while (enumeration.hasMoreElements()) {
ZipEntry zipEntry = (ZipEntry) enumeration.nextElement();
System.out.println(zipEntry.getSize()); // prints the size
}
如何从输入流中获取数据?
如果要检查解压缩的数据是否等于原始输入数据,可以从输入流中读取,如下所示:
byte[] output = new byte[input.length];
entry = zipIn.getNextEntry();
zipIn.read(output);
System.out.println("Are they equal? " + Arrays.equals(input, output));
// and if we want the size
zipIn.getNextEntry(); // or zipIn.read();
System.out.println("and the size is " + entry.getSize());
现在output
应该具有与input
.