簡體   English   中英

如何將大文件(12gb)分成多個1GB壓縮(.gz)存檔? C#

[英]How to split big file(12gb) into multiple 1GB compressed(.gz) archives? C#

我有一個很大的.bak文件-接近12GB。 我需要將其拆分為多個2gb .gz歸檔文件。

最大的問題是,我以后需要驗證此存檔。

您知道當您使用Winrar在3個或4個壓縮文件上分割一個文件時,然后按“解壓”,它將全部解壓縮為一個文件,或者如果沒有足夠的壓縮文件則崩潰(刪除一個)。

我需要這樣的東西。

public void Compress(DirectoryInfo directorySelected)
{
    int writeStat = 0;

    foreach (FileInfo fileToCompress in directorySelected.GetFiles())
    {
        using (FileStream originalFileStream = fileToCompress.OpenRead())
        {
            if ((File.GetAttributes(fileToCompress.FullName) &
               FileAttributes.Hidden) != FileAttributes.Hidden & fileToCompress.Extension != ".gz")
            {
                bytesToRead = new byte[originalFileStream.Length];
                int numBytesRead = bytesToRead.Length;

                while (_nowOffset < originalFileStream.Length)
                {                                
                    writeStat = originalFileStream.Read(bytesToRead, 0, homMuchRead);

                    using (FileStream compressedFileStream = File.Create(fileToCompress.FullName + counter + ".gz"))
                    {
                        using (GZipStream compressionStream = new GZipStream(compressedFileStream,
                           CompressionMode.Compress))
                        {
                            compressionStream.Write(bytesToRead, 0, writeStat);
                        }
                    }
                    _nowOffset = _nowOffset + writeStat;                        
                    counter++;
                }
                FileInfo info = new FileInfo(directoryPath + Path.DirectorySeparatorChar + fileToCompress.Name + ".gz");
                //Console.WriteLine($"Compressed {fileToCompress.Name} from {fileToCompress.Length.ToString()} to {info.Length.ToString()} bytes.");
            }
        }
    }
}

它運作良好,但我不知道如何驗證其計數。

我在測試對象上有7個存檔。 但是如何在一個文件中讀取它們,並驗證該文件已滿。

GZip格式本身不支持您想要的。

Zip確實將其稱為“跨區存檔”,但.NET中的ZipArchive類卻沒有。 為此,您需要一個第三方庫,例如DotNetZip

但是有解決方法。

創建一個類,該類繼承自Stream抽象,從外部來說,它是一個只能寫入但不能讀取或查找的流,在實現中寫入多個片段,每個2GB。 在實現中使用.NET提供的FileStream。 在班級long ,跟蹤所寫的總長度。 下一次Write()調用將超過2GB時,立即寫入足夠的字節以達到2GB,關閉並處置基礎FileStream,使用下一個文件名打開另一個文件,將文件長度計數器重置為0,然后從您調用Write()的緩沖區。 重復直到關閉。

創建您的自定義流的實例,傳遞給GZipStream的構造函數,然后將完整的12GB源數據復制到GZipStream中。

如果操作正確,則輸出的文件大小恰好為2GB(最后一個除外)。

要讀取和解壓縮它們,您需要使用自定義流實現類似的技巧。 編寫一個流類,將多個文件動態地連接起來,假裝它是單個流,但是這次您只需要實現Read()方法。 將連接流從框架提供給GZipStream 如果您要重新排序或銷毀某些零件,則GZipStream可能無法解壓縮,抱怨CRC校驗和的可能性很高(但不是100%)。

PS為了實現和調試上述2個流,我建議使用更小的數據集,例如12 MB的數據,分成1MB的壓縮段。 一旦使它起作用,請增加常量並使用完整的12GB數據進行測試。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM