求助:无法将GZIP字节数组解压为MemoryStream,Read返回0
问题分析与修复
你遇到的核心问题是:写入字节数组到MemoryStream后,流的Position指针停在了数组末尾,此时GZipStream从这个位置开始读取,自然读不到任何数据。FileStream能正常工作是因为文件流打开时默认Position在起始位置,但MemoryStream执行Write操作后,指针会移动到写入内容的结尾。
修复方案
方案1:手动重置源流的Position
在创建GZipStream之前,把srcStream的Position重置到0:
Private Function DecompressByteArray(bytes As Byte()) As System.IO.MemoryStream Dim srcStream As New System.IO.MemoryStream Dim destStream As New System.IO.MemoryStream srcStream.Write(bytes, 0, bytes.Length) srcStream.Position = 0 ' 关键:将流指针移回起始位置 Dim gz As New System.IO.Compression.GZipStream(srcStream, System.IO.Compression.CompressionMode.Decompress) Dim bytesRead As Integer Dim buffer As Byte() = New Byte(10000) {} bytesRead = gz.Read(buffer, 0, buffer.Length) While bytesRead <> 0 destStream.Write(buffer, 0, bytesRead) bytesRead = gz.Read(buffer, 0, buffer.Length) End While gz.Close() srcStream.Close() destStream.Position = 0 ' 重置目标流指针,方便调用者读取 Return destStream End Function
方案2:直接用字节数组初始化MemoryStream(更简洁)
MemoryStream提供了直接接收字节数组的构造函数,初始化后的流默认Position就在0,省去手动写入和重置的步骤:
Private Function DecompressByteArray(bytes As Byte()) As System.IO.MemoryStream Dim destStream As New System.IO.MemoryStream() ' 直接用字节数组初始化源流,Position默认在0 Using srcStream As New System.IO.MemoryStream(bytes) Using gz As New System.IO.Compression.GZipStream(srcStream, System.IO.Compression.CompressionMode.Decompress) Dim buffer As Byte() = New Byte(10000) {} Dim bytesRead As Integer Do bytesRead = gz.Read(buffer, 0, buffer.Length) If bytesRead > 0 Then destStream.Write(buffer, 0, bytesRead) End If Loop While bytesRead <> 0 End Using ' 自动释放GZipStream资源 End Using ' 自动释放MemoryStream资源 destStream.Position = 0 Return destStream End Function
额外优化说明
- 使用
Using语句替代手动调用Close(),能确保即使发生异常,流资源也会被正确释放,避免内存泄漏。 - 返回
destStream前设置Position = 0,是为了让调用方可以直接从流的起始位置读取内容,无需手动重置指针。
内容的提问来源于stack exchange,提问作者Dan H.
相关产品推荐
相关产品推荐

