代码之家  ›  专栏  ›  技术社区  ›  josh3736

DeflateStream不解压缩数据(第一次)

  •  8
  • josh3736  · 技术社区  · 15 年前

    所以这里有一个奇怪的。我使用此方法获取Base64编码的压缩字符串并返回原始数据:

    public static string Base64Decompress(string base64data)
    {
        byte[] b = Convert.FromBase64String(base64data);
        using (var orig = new MemoryStream(b))
        {
            using (var inflate = new MemoryStream())
            {
                using (var ds = new DeflateStream(orig, CompressionMode.Decompress))
                {
                    ds.CopyTo(inflate);
                    return Encoding.ASCII.GetString(inflate.ToArray());
                }
            }
        }
    }
    

    返回空字符串 除非 我再打一个电话给 ds.CopyTo(inflate)

       ...
                using (var ds = new DeflateStream(orig, CompressionMode.Decompress))
                {
                    ds.CopyTo(inflate);
                    ds.CopyTo(inflate);
                    return Encoding.ASCII.GetString(inflate.ToArray());
                }
       ...
    

    ( Flush / Close / Dispose ds

    为什么 DeflateStream Read() ,但它在第一次调用时也返回零,然后在第二次调用时返回零。


    更新:
    public static string Base64Compress(string data, Encoding enc)
    {
        using (var ms = new MemoryStream())
        {
            using (var ds = new DeflateStream(ms, CompressionMode.Compress))
            {
                byte[] b = enc.GetBytes(data);
                ds.Write(b, 0, b.Length);
                ds.Flush();
                return Convert.ToBase64String(ms.ToArray());
            }
        }
    }
    
    1 回复  |  直到 15 年前
        1
  •  7
  •   Chris Baxter    15 年前

    当压缩字节不完整时(即并非所有块都被写出)就会发生这种情况。

    如果我将Base64Compress与以下解压缩方法一起使用,将得到消息“未知块类型”的InvalidDataException。流可能已损坏

    减压

    public static string Decompress(Byte[] bytes)
    {
      using (var uncompressed = new MemoryStream())
      using (var compressed = new MemoryStream(bytes))
      using (var ds = new DeflateStream(compressed, CompressionMode.Decompress))
      {
        ds.CopyTo(uncompressed);
        return Encoding.ASCII.GetString(uncompressed.ToArray());
      }
    }
    

    public Byte[] Compress(Byte[] bytes)
    {
      using (var memoryStream = new MemoryStream())
      {
        using (var deflateStream = new DeflateStream(memoryStream, CompressionMode.Compress))
          deflateStream.Write(bytes, 0, bytes.Length);
    
        return memoryStream.ToArray();
      }
    }
    

    更新

    哎呀,我真傻。。。在释放Deflate stream之前,不能排列内存流(因为flush实际上没有实现(以及Deflate/GZip压缩数据块);最后一个块只写在close/dispose上。

    public static string Base64Compress(string data, Encoding enc)
    {
      using (var ms = new MemoryStream())
      {
        using (var ds = new DeflateStream(ms, CompressionMode.Compress))
        {
          byte[] b = enc.GetBytes(data);
          ds.Write(b, 0, b.Length);
        }
    
        return Convert.ToBase64String(ms.ToArray());
      }
    }