简体   繁体   English

如何使用gzipstream将内存流压缩成内存流?

[英]How to compress memory stream into memory stream using gzipstream?

Hello my problem is that I need to compress MemoryStream with GZipStream into MemoryStream if possible into the same MemoryStream that method gets as parameter.你好,我的问题是,如果可能的话,我需要将带有 GZipStream 的 MemoryStream 压缩到 MemoryStream 到该方法作为参数获取的相同 MemoryStream 中。 If this can't be achieved how can I make it so it is the most memory efficient.如果这无法实现,我该如何使它成为最有效的内存。


Here is my current method and it is giving me System.NotSupportedException: 'Stream does not support reading.'这是我当前的方法,它给了我System.NotSupportedException: 'Stream 不支持阅读。' for compress.CopyTo用于 compress.CopyTo

public static void GZipCompress(MemoryStream memoryStream)
{
    using (GZipStream compress = new GZipStream(memoryStream, CompressionMode.Compress))
    {
        compress.CopyTo(memoryStream);
    }
}

You can't copy the stream to itself, at least not without a lot of work.您不能将流复制到自身,至少在没有大量工作的情况下不能。 Just allocating a new MemoryStream for the compressed data is simple and reasonably efficient.只需为压缩数据分配一个新的 MemoryStream 就很简单而且相当有效。 eg例如

public MemoryStream GZipCompress(MemoryStream memoryStream)
{
    var newStream = new MemoryStream((int)memoryStream.Length / 2); //set to estimate of compression ratio

    using (GZipStream compress = new GZipStream(newStream, CompressionMode.Compress))
    {
        memoryStream.CopyTo(compress);
    }
    newStream.Position = 0;
    return newStream;
}

Here's an untested idea for how to perform in-place compression of a MemoryStream.这是关于如何执行 MemoryStream 的就地压缩的未经测试的想法。

public void GZipCompress(MemoryStream memoryStream)
{
    var buf = new byte[1024 * 64];
    int writePos = 0;

    using (GZipStream compress = new GZipStream(memoryStream, CompressionMode.Compress))
    {
        while (true)
        {
            var br = compress.Read(buf, 0, buf.Length);
            if (br == 0) //end of stream
            {
                break;
            }
            var readPos = memoryStream.Position;
            memoryStream.Position = writePos;
            memoryStream.Write(buf, 0, br);
            writePos += br;

            if (memoryStream.Position > readPos)
            {
                throw new InvalidOperationException("Overlapping writes corrupted the stream");
            }
            memoryStream.Position = readPos;
        }
    }
    memoryStream.SetLength(writePos);
    memoryStream.Position = 0;
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM