【发布时间】:2017-01-18 16:28:23
【问题描述】:
我想在序列化时压缩 ProtoBuffer 对象并在反序列化时解压缩。不幸的是,C# stdlib 只提供了对流而不是字节 [] 工作的压缩例程,这使得它比函数调用更冗长一些。到目前为止我的代码:
class MyObject{
public string P1 {get; set;}
public string P2 {get; set;}
// ...
public byte[] Serialize(){
var builder = new BinaryFormat.MyObject.Builder();
builder.SetP1(P1);
builder.SetP2(P2);
// ...
// object is now build, let's compress it.
var ms = new MemoryStream();
// Without this using, the serialisatoin/deserialisation Tests fail
using (var gz = new GZipStream(ms, CompressionMode.Compress))
{
builder.Build().WriteTo(gz);
}
return ms.ToArray();
}
public void Deserialize(byte[] data)
{
var ms = new MemoryStream();
// Here, Tests work, even when the "using" is left out, like this:
(new GZipStream(new MemoryStream(data), CompressionMode.Decompress)).CopyTo(ms);
var msg = BinaryFormat.MachineInfo.ParseFrom(ms.ToArray());
P1 = msg.P1;
P2 = msg.P2;
// ...
}
}
在处理流时,似乎必须手动处理对象的处理。我想知道为什么会这样,我希望 GZipStream 是完全托管的代码。而且我想知道 Deserialize 是否只是偶然起作用,我是否也应该处理 MemoryStreams。
我知道我可以通过简单地使用第三方压缩库来解决这个问题,但这有点超出了这个问题的重点。
【问题讨论】:
-
如果我没记错的话,
MemoryStream在拥有对象时被处理掉了,在这种情况下,GZipStream被处理掉了。或者那可能只是为了Images... -
好吧,把它当作一个学习曲线,如果有东西实现了
IDisposable,它应该被处理掉,最好使用using。编写代码以正确使用和处理对象,而您一开始就不会发现问题。 -
-
@ScottChamberlain 这更像是一个笼统的评论,因为总是有边缘情况,但它们超出了问题的范围
-
编译器不应该警告我这个陷阱吗?对我来说,GZipStream 甚至实现了 IDisposable 并不明显。这个 BTW 在 GC 语言中感觉很奇怪。
标签: c# idisposable gzipstream