如何使用7z SDK压缩和解压缩文件

本文关键字:解压缩 文件 压缩 SDK 何使用 7z | 更新日期: 2023-09-27 18:10:18

根据这个链接,我如何用。net创建7-Zip档案?, WOPR告诉我们如何使用7z SDK (http://www.7-zip.org/sdk.html)用LMZA (7z压缩算法)压缩文件

using SevenZip.Compression.LZMA;
private static void CompressFileLZMA(string inFile, string outFile)
{
   SevenZip.Compression.LZMA.Encoder coder = new SevenZip.Compression.LZMA.Encoder();
   using (FileStream input = new FileStream(inFile, FileMode.Open))
   {
      using (FileStream output = new FileStream(outFile, FileMode.Create))
      {
          coder.Code(input, output, -1, -1, null);
          output.Flush();
      }
   }
}

但是如何解压呢?

I try:

private static void DecompressFileLZMA(string inFile, string outFile)
        {
            SevenZip.Compression.LZMA.Decoder coder = new SevenZip.Compression.LZMA.Decoder();
            using (FileStream input = new FileStream(inFile, FileMode.Open))
            {
                using (FileStream output = new FileStream(outFile, FileMode.Create))
                {
                    coder.Code(input, output, input.Length, -1, null);
                    output.Flush();
                }
            }
        }

但没有成功。

你有一个工作的例子吗?

感谢

PS:根据另一个代码http://www.koders.com/csharp/fid43E85EE5AE7BB255C69D18ECC3288285AD67A4A4.aspx?s=zip+encoder#L5,解码器似乎需要一个头,一个在文件开头的字典才能工作。这个由Koders生成的文件不是一个7z归档文件。

   public static void Decompress(Stream inStream, Stream outStream)
    {
        byte[] properties = new byte[5];
        inStream.Read(properties, 0, 5);
        SevenZip.Compression.LZMA.Decoder decoder = new SevenZip.Compression.LZMA.Decoder();
        decoder.SetDecoderProperties(properties);
        long outSize = 0;
        for (int i = 0; i < 8; i++)
        {
            int v = inStream.ReadByte();
            outSize |= ((long)(byte)v) << (8 * i);
        }
        long compressedSize = inStream.Length - inStream.Position;
        decoder.Code(inStream, outStream, compressedSize, outSize, null);
    }

outSize的计算方式与它们的Compress方法相同。但是如何计算输出大小呢?

如何使用7z SDK压缩和解压缩文件

这个问题有点老了,但谷歌没有提供一个令人满意的答案,所以这是给那些像我一样仍在寻找它的人的。如果您查看SDK的LMZAAlone文件夹,那里有压缩和解压缩文件的代码。以它为例,似乎您需要写入和读取编码器属性并将文件大小解压缩到输出文件:

private static void CompressFileLZMA(string inFile, string outFile)
    {
        SevenZip.Compression.LZMA.Encoder coder = new SevenZip.Compression.LZMA.Encoder();
        FileStream input = new FileStream(inFile, FileMode.Open);
        FileStream output = new FileStream(outFile, FileMode.Create);
        // Write the encoder properties
        coder.WriteCoderProperties(output);
        // Write the decompressed file size.
        output.Write(BitConverter.GetBytes(input.Length), 0, 8);
        // Encode the file.
        coder.Code(input, output, input.Length, -1, null);
        output.Flush();
        output.Close();
    }
    private static void DecompressFileLZMA(string inFile, string outFile)
    {
        SevenZip.Compression.LZMA.Decoder coder = new SevenZip.Compression.LZMA.Decoder();
        FileStream input = new FileStream(inFile, FileMode.Open);
        FileStream output = new FileStream(outFile, FileMode.Create);
        // Read the decoder properties
        byte[] properties = new byte[5];
        input.Read(properties, 0, 5);
        // Read in the decompress file size.
        byte [] fileLengthBytes = new byte[8];
        input.Read(fileLengthBytes, 0, 8);
        long fileLength = BitConverter.ToInt64(fileLengthBytes, 0);
        coder.SetDecoderProperties(properties);
        coder.Code(input, output, input.Length, fileLength, null);
        output.Flush();
        output.Close();
    }

请注意,以这种方式创建的文件也可以由7zip程序提取,但不会保留其文件名或任何其他元数据。

我需要LZMA压缩通过网络发送图像,不确定这是最好的选择,但至少它在我的生态系统中工作!因此,这里有一些东西应该可以立即达到这个目的。

using System;
using System.IO;
using SevenZip;
  public class LZMA{
    public static byte[] Compress(byte[] toCompress)
      {
        SevenZip.Compression.LZMA.Encoder coder = new SevenZip.Compression.LZMA.Encoder();
        using(MemoryStream input = new MemoryStream(toCompress))
        using(MemoryStream output = new MemoryStream()){
          coder.WriteCoderProperties(output);
          for (int i = 0; i < 8; i++) {
            output.WriteByte((byte)(input.Length >> (8 * i)));
          }
          coder.Code(input, output, -1, -1, null);
          return output.ToArray();
        }
      }
    public static byte[] Decompress(byte[] toDecompress)
    {
        SevenZip.Compression.LZMA.Decoder coder = new SevenZip.Compression.LZMA.Decoder();
        using(MemoryStream input = new MemoryStream(toDecompress))
        using(MemoryStream output = new MemoryStream()){
          // Read the decoder properties
          byte[] properties = new byte[5];
          input.Read(properties, 0, 5);

          // Read in the decompress file size.
          byte [] fileLengthBytes = new byte[8];
          input.Read(fileLengthBytes, 0, 8);
          long fileLength = BitConverter.ToInt64(fileLengthBytes, 0);
          coder.SetDecoderProperties(properties);
          coder.Code(input, output, input.Length, fileLength, null);
          return output.ToArray();
        }
    }
  }

我强烈推荐:
https://github.com/weltkante/managed-lzma

在文件编码中保留文件信息和目录结构