Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/331.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 压缩流_C#_Stream_Compression - Fatal编程技术网

C# 压缩流

C# 压缩流,c#,stream,compression,C#,Stream,Compression,我一直在尝试在我的一个程序中实现一种压缩方法。我希望它接收一个流,对其进行压缩,然后返回压缩后的流(它返回一个流,因为我希望能够将流传递给另一个函数,而不必将其保存到文件中并在以后重新读取)。我有一个基于msdn示例的工作测试版本,这是我在尝试将其转换为接收和返回流时想到的: public static Stream compress(Stream fileToCompress) { using (MemoryStream compressedFileStream = new Memor

我一直在尝试在我的一个程序中实现一种压缩方法。我希望它接收一个流,对其进行压缩,然后返回压缩后的流(它返回一个流,因为我希望能够将流传递给另一个函数,而不必将其保存到文件中并在以后重新读取)。我有一个基于msdn示例的工作测试版本,这是我在尝试将其转换为接收和返回流时想到的:

public static Stream compress(Stream fileToCompress)
{
    using (MemoryStream compressedFileStream = new MemoryStream())
    {
        using (GZipStream compressionStream = new GZipStream(compressedFileStream, CompressionMode.Compress))
        {
            fileToCompress.CopyTo(compressionStream);
            return compressionStream;
        }
    }
}
将返回的流保存到文件(在另一种方法中)会导致创建一个0字节的文件(相当高效的压缩,嗯?)

我已经试着寻找,但我没有找到任何使用流的,我尝试转换运行到相同的问题

编辑:为了记录在案,我尝试使用DeflateStream获得相同的结果


EDIT2:原来是测试程序没有正确保存。感谢您的帮助。

如果您的目标是返回流,则不需要使用将其放入

大概是这样的:

public static Stream compress(Stream fileToCompress) {
    MemoryStream compressedFileStream = new MemoryStream();
    GZipStream compressionStream = new GZipStream(compressedFileStream, CompressionMode.Compress);
    fileToCompress.CopyTo(compressionStream);
    compressionStream.Seek(0, SeekOrigin.Begin); // Reset to stream start.
    return compressionStream;
}
否则,当流使用
块离开
时,它将调用流上的
Dispose()

编辑:同样,在复制之后,流“指针”位于末尾。您需要将指针设置回起始位置。保存前-如图所示


编辑:删除所有使用块。如果您需要释放流,可以手动执行。

您可以按照Steven Hansen的建议,使用
/
Dispose
调用跳过
,但使用压缩数据返回
MemoryStream
的新副本可能会更干净

public static Stream compress(Stream fileToCompress)
{
    using (MemoryStream compressedFileStream = new MemoryStream())
    {
        using (var compressionStream = new GZipStream(
             compressedFileStream, CompressionMode.Compress))
        {
            fileToCompress.CopyTo(compressionStream);
        }
        return new MemoryStream(compressionStream.ToArray());
    }
}
如果只想保留单个内存流,请使用调用删除,不要忘记重新定位该流

var compressedFileStream = new MemoryStream();
var compressionStream = new GZipStream(
           compressedFileStream, CompressionMode.Compress);
fileToCompress.CopyTo(compressionStream);
 // Flush to make sure all data written by compression stream.
compressionStream.Flush();
compressedFileStream.Position = 0;
return compressedFileStream;

请注意,如果您的文件非常大,使用临时文件存储压缩/未压缩流可能会更快,因为
MemoryStream
中使用了内存分配策略-请尝试这两种方法并进行测量。

请注意,您的示例实际上关闭了底层流,这将导致相同的“读取/写入已处理流”例外。我不能100%确定
MemoryStream
GZipStream
的交互作用,所以我相信你的话。我的编辑删除了使用。感谢您的快速响应。我想我以前试过,但没用。我又试了一次,只是想确定一下,但我还是遇到了这个问题。另外@AlexeiLevenkov,它没有抛出任何异常,它只是返回一个空流。@user3299958-我在我的帖子中放了一个应该有用的示例。请确保阅读此搜索中涉及0字节文件问题的答案。我已编辑以显示查找
流的代码。在您保存之前,需要这样做。