4

誰かが私を悩ませている問題に光を当てることができるのだろうか:

圧縮解凍テストクラスを作成しています。それをテストするために、データセットをメモリストリームにシリアル化し、圧縮し、解凍して結果を比較しています。

圧縮は問題ありませんが、非圧縮はそれが汚れに当たる場所です。これは解凍機能です。

    public static Stream GetUncompressedStreamCopy(Stream inStream)
    {
      Stream outStream = new MemoryStream();

      inStream.Position = 0;

      DeflateStream uncompressStream = new DeflateStream(inStream, 
        CompressionMode.Decompress, true);

      byte[] buffer = new byte[65536];

      int totalread = 0;
      int bytesread = 0;


      do {
        bytesread = uncompressStream.Read(buffer, 0, buffer.Length);
        totalread += bytesread;
        outStream.Write(buffer, 0, bytesread);
        Console.WriteLine("bytesRead: [{0}]\t outStream.Length [{1}]",
        bytesread, outStream.Length);
      } while (bytesread > 0);


      Console.WriteLine("total bytes read [{0}]", totalread);
      outStream.Flush();
      return outStream;
}

サイズ65536のバッファを使用すると、解凍されたストリームは、圧縮されていない場合よりも常に1バイト少なくなります。

今、これは私が戦っている2番目の問題に私をもたらします。一部のバッファサイズでは、抽出する圧縮データがまだ残っている場合でも、uncompressStream.Readは0を返します。

このような場合、deflateStream.Read(s)はdo {}ループで1回だけ実行され、バッファサイズを1バイト増やすと、バッファサイズに等しい非圧縮ストリームが返されます(欠落しているバイトを除く)。

65536のバッファサイズの出力:(元の非圧縮データは207833です)

bytesRead: [65536]       outStream.Length [65536]
bytesRead: [65536]       outStream.Length [131072]
bytesRead: [58472]       outStream.Length [189544]
bytesRead: [18288]       outStream.Length [207832]
bytesRead: [0]           outStream.Length [207832]
total bytes read [207832]

189544のbuffersize(コードがタンクに入るいくつかのマジックナンバー)

bytesRead: [189544]      outStream.Length [189544]
bytesRead: [0]           outStream.Length [189544]
total bytes read [189544]
Unompressed stream size 189544

また、バッファサイズ65536の3番目の読み取りに注意してください。例:bytesRead:[58472]バッファにまだデータが残っているので、明らかにこれも65536である必要がありますか?

どんなアイデアでも歓迎です。

tia

  • ジャコ
4

3 に答える 3

7

圧縮ストリームでは常にClose()を呼び出す必要があります。Flush()では不十分であることに注意してください。このため、デフレートストリームにデータが欠落していると思われます。

于 2009-10-22T14:29:23.410 に答える
3

私の超能力によると、実際には解凍の実装は機能していますが、以前に圧縮ストリームをフラッシュするのを忘れていました。

于 2009-10-22T14:25:24.957 に答える
0

さて、私はあなたの問題を見つけることができませんでしたが、ICSharpCode.SharpZipLibのために私が以前に書いたいくつかのコードに従ってください。

byte[] compressedData;
using(MemoryStream ms = new MemoryStream())
{
    Deflater deflater = new Deflater(Deflater.BEST_COMPRESSION, true);
    Stream s = new DeflaterOutputStream(ms, deflater);
    s.Write(sendData, 0, sendData.Length);
    s.Close();
    compressedData = (byte[])ms.ToArray();
}

// ...

MemoryStream inflated = new MemoryStream();
using (Stream inflater = new InflaterInputStream(
    inputStream, new Inflater(true)))
{
    int count = 0;
    byte[] deflated = new byte[4096];
    while ((count = inflater.Read(deflated, 0, deflated.Length)) != 0)
    {
        inflated.Write(deflated, 0, count);
    }
    inflated.Seek(0, SeekOrigin.Begin);
}
byte[] content = new byte[inflated.Length];
inflated.Read(content, 0, content.Length);
于 2009-10-22T14:30:20.097 に答える