多くの場合、アーカイブのネストされた構造を形成する他のZIPアーカイブを含むZIPアーカイブを取得します。このような場合、すべての内部ZIPアーカイブを外部アーカイブに抽出してフラットな構造にすることができます。この操作をプログラムで実行するために、この記事では、C#でフラットZIPアーカイブを作成する方法を示します。

フラットZIPアーカイブを作成するためのC#.NET API

フラットZIPアーカイブを作成するには、Aspose.ZIP for.NETを使用します。これは、ZIP、TAR、GZip、7zなどの一般的なアーカイブ形式を作成および抽出するように設計されたアーカイブAPIです。 NuGetからAPIをインストールするか、ダウンロードセクションからDLLをダウンロードできます。

PM> Install-Package Aspose.Zip

C#でフラットZIPアーカイブを作成する

フラットZIPアーカイブの構造を理解するために、例を見てみましょう。以下は、その中に別のZIPアーカイブを含むZIPアーカイブです。

parent.zip
 ├first.txt
 ├inner.zip
 │ ├game.exe
 │ └subitem.bin
 └picture.gif

このZIPアーカイブをフラットZIPに変換した後、内部ZIPのすべてのエントリが親ZIPに抽出されます。最後に、親ZIPの次の構造を取得します。

flatten.zip
 ├first.txt
 ├picture.gif
 ├game.exe
 └subitem.bin

この変換をプログラムで実行する方法を見てみましょう。以下は、C#でフラットZIPアーカイブを作成する手順です。

  • まず、Archiveクラスを使用して親ZIPアーカイブをロードします。
  • 次に、親ZIPから削除する内部ZIPエントリ、抽出されたエントリ、およびそれらの名前を格納するリストを作成します。
  • その後、Archive.Entriesコレクションを使用して、親ZIPの各ArchiveEntryをループします。
  • エントリごとに、次の操作を実行します。
    • ArchiveEntry.Name.EndsWith( “。zip”、StringComparison.InvariantCultureIgnoreCase))メソッドを使用して、エントリがZIPアーカイブであるかどうかを確認します。
    • 次に、削除するエントリのリストにエントリを追加します。
    • ArchiveEntry.Open().CopyTo(MemoryStream)メソッドを使用して、MemoryStreamオブジェクトへのエントリを開きます。
    • 内部ZIPアーカイブのエントリを繰り返し処理し、各繰り返しで次の手順を実行します。
      • 追加するエントリのリストにエントリの名前を追加します。
      • 次に、ArchiveEntry.Open().CopyTo(MemoryStream)メソッドを使用してMemoryStreamにエントリをロードします。
      • 最後に、親ZIPに追加するエントリのリストにエントリを追加します。
  • 次に、内部ZIPアーカイブのリストをループし、Archive.DeleteEntry(ArchiveEntry)メソッドを使用して各エントリを削除します。
  • 親ZIPに追加するエントリのリストをループし、Archive.CreateEntry(String, Stream)メソッドを使用して各エントリを追加します。
  • 最後に、Archive.Save(String)メソッドを使用して親ZIPアーカイブを保存します。

次のコードサンプルは、C#でフラットZIPアーカイブを作成する方法を示しています。

// ZIPアーカイブをロード
using (Archive outer = new Archive("Archives/nested-archive.zip"))
{
    // 抽出後に内部ZIPエントリを削除するリストを作成する
    List<ArchiveEntry> entriesToDelete = new List<ArchiveEntry>();

    // 内部ZIPアーカイブ内のファイルの名前を追加するためのリストを作成します
    List<string> namesToInsert = new List<string>();

    // 内部ZIPアーカイブにファイルのストリームオブジェクトを追加するためのリストを作成します
    List<MemoryStream> contentToInsert = new List<MemoryStream>();

    // 親ZIPのエントリをループする
    foreach (ArchiveEntry entry in outer.Entries)
    {
        // エントリがZIPファイルかどうかを確認します
        if (entry.Name.EndsWith(".zip", StringComparison.InvariantCultureIgnoreCase)) 
        {
            // 後でアーカイブから削除するために参照を保持するためにリストにエントリを追加します
            entriesToDelete.Add(entry); 

            // ストリームオブジェクトを作成してZIPアーカイブを開きます
            MemoryStream innerCompressed = new MemoryStream();
            entry.Open().CopyTo(innerCompressed);

            // ストリームオブジェクトからZIPアーカイブをロードします 
            using (Archive inner = new Archive(innerCompressed))
            {
                // アーカイブのエントリをループする
                foreach (ArchiveEntry ie in inner.Entries) 
                {
                    // リストにエントリの名前を保持します
                    namesToInsert.Add(ie.Name); 

                    // アーカイブエントリをストリームオブジェクトに抽出します
                    MemoryStream content = new MemoryStream();
                    ie.Open().CopyTo(content);

                    // リストにエントリを追加します
                    contentToInsert.Add(content);
                }
            }
        }
    }

    // 内部のZIPアーカイブを削除する
    foreach (ArchiveEntry e in entriesToDelete)
        outer.DeleteEntry(e);

    // 内部ZIPアーカイブのファイルを親ZIPアーカイブに挿入します
    for (int i = 0; i < namesToInsert.Count; i++)
        outer.CreateEntry(namesToInsert[i], contentToInsert[i]);

    outer.Save("Archives/flatten.zip");
}

無料のAPIライセンスを取得する

無料の一時ライセンスを取得して、評価の制限なしにAspose.ZIPfor.NETを使用できます。

結論

この記事では、C#でプログラムでフラットZIPアーカイブを作成する方法を学びました。特に、内部のZIPアーカイブを親のZIPに抽出して、フラットなZIPを作成する方法を示しました。それとは別に、ドキュメントにアクセスして、Aspose.ZIPfor.NETの詳細を読むことができます。また、フォーラムを介してクエリを共有することもできます。

関連項目