[英]GZipStream works when writing to FileStream, but not MemoryStream
If compress some json text, and write that it to a file using a FileStream
I get the expected results. 如果压缩一些json文本,并使用
FileStream
将其写入文件,我会得到预期的结果。 However, I do not want to write to disk. 但是,我不想写入磁盘。 I simply want to memorystream of the compressed data.
我只想要压缩数据的内存流。
Compression to FileStream
: 压缩到
FileStream
:
string json = Resource1.json;
using (MemoryStream input = new MemoryStream(Encoding.UTF8.GetBytes(json)))
using (FileStream output = File.Create(@"C:\Users\roarker\Desktop\output.json.gz"))
{
using (GZipStream compression = new GZipStream(output, CompressionMode.Compress))
{
input.CopyTo(compression);
}
}
Above works. 以上作品。 Below, the output memory stream is length 10 and results in an empty .gz file.
下面,输出内存流的长度为10,并产生一个空的.gz文件。
string json = Resource1.json;
using (MemoryStream input = new MemoryStream(Encoding.UTF8.GetBytes(json)))
using (MemoryStream output = new MemoryStream())
{
using (GZipStream compression = new GZipStream(output, CompressionMode.Compress))
{
input.CopyTo(compression);
byte[] bytes = output.ToArray();
}
}
EDIT: Moving output.ToArray()
outside the inner using
clause seems to work. 编辑:在内部
using
子句之外移动output.ToArray()
似乎工作。 However, this closes the output stream for most usage. 但是,这会关闭大多数用法的输出流。 IE:
IE:
using (MemoryStream input = new MemoryStream(Encoding.UTF8.GetBytes(json)))
using (MemoryStream output = new MemoryStream())
{
using (GZipStream compression = new GZipStream(output, CompressionMode.Compress))
{
input.CopyTo(compression);
}
WriteToFile(output);
}
where : 其中:
public static void WriteToFile(Stream stream)
{
using (FileStream output = File.Create(@"C:\Users\roarker\Desktop\output.json.gz"))
{
stream.CopyTo(output);
}
}
This will fail on stream.CopyTo because the stream has been closed. 这将在stream.CopyTo失败,因为流已关闭。 I know I could make a new
Stream
from bytes of output.ToArray()
, but why is this necessary? 我知道我可以从
output.ToArray()
字节创建一个新的Stream
,但为什么这是必要的? why does ToArray()
work when the stream is closed? 为什么
ToArray()
在流关闭时工作?
Final Edit: 最终编辑:
Just needed to use the contructor of the GZipStream
with the leaveOpen
parameter. 只需要使用带有
leaveOpen
参数的GZipStream
的leaveOpen
函数。
You're calling ToArray()
before you've closed the GZipStream
... that means it hasn't had a chance to flush the final bits of its buffer. 你在关闭
GZipStream
之前调用ToArray()
...这意味着它没有机会刷新缓冲区的最后一位。 This is a common issue for compression an encryption streams, where closing the stream needs to write some final pieces of data. 这是压缩加密流的常见问题,关闭流需要编写一些最终的数据。 (Even calling
Flush()
explicitly won't help, for example.) (例如,即使调用
Flush()
也无济于事。)
Just move the ToArray
call: 只需移动
ToArray
调用:
using (MemoryStream input = new MemoryStream(Encoding.UTF8.GetBytes(json)))
using (MemoryStream output = new MemoryStream())
{
using (GZipStream compression = new GZipStream(output, CompressionMode.Compress))
{
input.CopyTo(compression);
}
byte[] bytes = output.ToArray();
// Use bytes
}
(Note that the stream will be disposed when you call ToArray
, but that's okay.) (请注意,当您调用
ToArray
,将处理该流,但这没关系。)
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.