Как создать функцию обратного вызова для функции LZMA (7zip) SDK encoder.Code ()? - PullRequest
0 голосов
/ 12 февраля 2020

Ниже приведена небольшая выдержка из класса, который я создаю для LZMA (7zip) SDK, найденного здесь . Похоже, что все работает нормально, но я пытаюсь внедрить некоторые отчеты о прогрессе, чтобы отслеживать ход процесса сжатия. В строке ниже encoder.Code(inStream, outStream, -1, -1, null); я использую null, когда мне нужно использовать некоторую форму обратного вызова ICodeProgress.

Я просто хочу создать некоторый тип обратного вызова делегата для отслеживания прогресса в потоке I создали в моем классе.

Выдержка из класса:

public class CompressorThreads : CompressorClassEvents
{
    public static class SevenZipCoderProperties
    {
        public static readonly CoderPropID[] PropertyNames =
        {
            CoderPropID.DictionarySize,
            CoderPropID.PosStateBits,
            CoderPropID.LitContextBits,
            CoderPropID.LitPosBits,
            CoderPropID.Algorithm,
            CoderPropID.NumFastBytes,
            CoderPropID.MatchFinder,
            CoderPropID.EndMarker,
        };

        public static readonly object[] PropertyValues =
        {
            (Int32)LzmaDictionarySize.VerySmall,
            (Int32)(2),
            (Int32)(3),
            (Int32)(0),
            (Int32)(2),
            (Int32)LzmaSpeed.Fastest,
            "bt4",
            true,
        };
    }


    private void Compress(string filePath, string compressedFilePath)
    {
        //Get the bytes of the file
        byte[] fileInBytes = File.ReadAllBytes(filePath);

        //Setup the encoder
        SevenZip.Compression.LZMA.Encoder encoder = new SevenZip.Compression.LZMA.Encoder();
        encoder.SetCoderProperties(SevenZipCoderProperties.PropertyNames, SevenZipCoderProperties.PropertyValues);

        using (MemoryStream outStream = new MemoryStream())
        {
            encoder.WriteCoderProperties(outStream);

            //Get the file bytes into a memory then compress them
            using (MemoryStream inStream = new MemoryStream(fileInBytes))
            {
                long uncompressedFilesize = inStream.Length;

                for (int i = 0; i < 8; i++)
                        outStream.WriteByte((Byte)(uncompressedFilesize >> (8 * i)));

                encoder.Code(inStream, outStream, -1, -1, null);
            }

            //Write the compressed file
            compressedFileSize = outStream.Length;
            using (FileStream file = new FileStream(compressedFilePath, FileMode.Create, FileAccess.Write))
            {
                outStream.WriteTo(file);
            }
        }
    }
}

1 Ответ

1 голос
/ 12 февраля 2020

ICodeProgress - это интерфейс, поэтому вам нужно его где-то реализовать. Вы можете реализовать интерфейс ICodeProgress в своем классе и передать this вместо null.

Например, вы бы сделали что-то вроде этого:

class CompressorThreads : CompressorClassEvents, ICodeProgress
{
    void ICodeProgress.SetProgress(long inSize, long outSize)
    {
        System.Diagnostics.Debug.WriteLine("processedInSize:" + inSize + "  processedOutSize:" + outSize);
    }
    private void Compress(string filePath, string compressedFilePath)
    {
        . . .
        encoder.Code(inStream, outStream, -1, -1, this);
        . . .
    }
}
...