我有Zip和Unzip Text的代码。我面临着奇怪的行为-仅当我在特定位置关闭GZIPOutputStream
时,代码才起作用,但是当我尝试将GZIPOutputStream close
放在finally块中时,它会中断并且不起作用。如果将gzipoutputstream.close()
放在放置注释的czip
函数中,它将起作用。但是,如果仅将其保留在finally
块中,它将损坏。为什么?
ByteStreams.copy
函数来自com.google.common.io guava
public class Main {
public static byte[] dzip(byte[] s) throws IOException {
ByteArrayInputStream sStream = null;
ByteArrayOutputStream oStream = null;
InputStream gzipoutputStream = null;
ByteBuffer arrReturn = null;
try {
sStream = new ByteArrayInputStream(s);
oStream = new ByteArrayOutputStream();
gzipoutputStream = new GZIPInputStream(sStream, 1024);
ByteStreams.copy(gzipoutputStream, oStream);
arrReturn = ByteBuffer.wrap(oStream.toByteArray());
}
catch (Exception e) {
return null;
} finally {
if (gzipoutputStream != null) {
gzipoutputStream.close();
}
if (oStream != null) {
oStream.close();
}
if (sStream != null) {
sStream.close();
}
}
return arrReturn.array();
}
public static byte[] czip(byte[] s) throws IOException {
ByteArrayInputStream sStream =null;
ByteArrayOutputStream oStream =null;
OutputStream gzipoutputstream = null;
byte[] returnValue = null;
try {
sStream = new ByteArrayInputStream(s);
oStream = new ByteArrayOutputStream(s.length / 2);
gzipoutputstream = new GZIPOutputStream(oStream, 1024);
ByteStreams.copy(sStream, gzipoutputstream);
//////////// ------------------------------------ \\\\\\\\\\\\
//gzipoutputstream.close(); // < --- Works only when placed here
//////////// ------------------------------------ \\\\\\\\\\\\
returnValue = oStream.toByteArray(); // Here the zip is 000
}catch(Exception e) {
return null;
} finally {
if (gzipoutputstream != null) {
gzipoutputstream.close();
}
if (oStream != null) {
oStream.close();
}
if (sStream != null) {
sStream.close();
}
}
return returnValue;
}
public static void main(String[] args) throws IOException {
String s = "12313dsfafafafaf";
byte[] source = (byte[]) s.getBytes();
byte[] returnZipByteArr = czip(source);
byte[] dd = dzip(returnZipByteArr);
String ss = new String(dd);
System.out.println(ss);
}
}
答案 0 :(得分:3)
这是预期的。 The javadoc of close()说:
将剩余的压缩数据写入输出流并关闭基础流。
因此,如果您在调用close()之前尝试访问ByteArrayOutputStream()中的字节,则gzip压缩尚未完成:GZIP流需要知道不会再写入任何内容才能正确写入其余数据。
您可以调用finish()
来达到相同的效果,但是不关闭流(因此仍然在finally块中将其关闭)。