.NET TIPS

GZIP形式でファイルを圧縮/解凍するには?[2.0のみ、C#、VB]

デジタルアドバンテージ 遠藤 孝信
2006/08/11

 .NET Framework 2.0には、ストリームをGZIP形式で圧縮/解凍*するためのGZipStreamクラス(System.IO.Compression名前空間)が新しく追加されている。GZIP形式はUNIXやLinuxで一般的に使用されている圧縮ツールである「gzipコマンド」で用いられている圧縮方式である。

* ヘルプではdecompressを「圧縮解除」と訳しているが、本稿ではより広く使われている訳語である「解凍」を用いる。

 本稿ではこのGZipStreamクラスを用いてファイルを圧縮/解凍する方法について解説する。

 なお、GZipStreamクラスはあくまでもストリームを圧縮/解凍するためのクラスであり、複数のファイルを1つのファイルに圧縮するなどの機能は持っていない(これを実現するためには複数のファイルを1つのファイルにまとめる処理を自分で実装する必要がある)。

GZipStreamクラスのコンストラクタ

 GZipStreamクラスでは、コンストラクタのパラメータにて圧縮を行うか解凍を行うかをまず指定する。圧縮を行う場合には次のようにしてコンストラクタを呼び出す。第2パラメータにはCompressionMode列挙体(System.IO.Compression名前空間)の値を指定する。

GZipStream compStream = new GZipStream(
    <出力先ストリーム>, CompressionMode.Compress)

 このようにして作成したGZipStreamオブジェクトでは、WriteメソッドやWriteByteメソッドにより、指定したバッファ内のデータを圧縮して<出力先ストリーム>に書き込むことができる。

 一方、解凍を行う場合にはコンストラクタの呼び出しは次のようになる。

GZipStream decompStream = new GZipStream(
    <入力元ストリーム>, CompressionMode.Decompress)

 この場合には、ReadメソッドやReadByteメソッドにより、<入力元ストリーム>から読み込んだデータを解凍し、指定したバッファに出力できる。

ファイルを圧縮するサンプル・プログラム

 次に示すサンプル・プログラムは、実行時に指定されたファイルを圧縮し、圧縮ファイルである「ファイル名.gz」を作成する。

 このプログラムでは、ファイル・ストリームから読み込んだデータを圧縮ストリーム(GZipStreamオブジェクト)に書き込んでいる。圧縮ストリームの出力先には、出力ファイル用のファイル・ストリームをコンストラクタでセットしている。

// gzcomp.cs

using System;
using System.IO;
using System.IO.Compression;

public class CompressSample {
  static void Main(string[] args) {

    string inFile = args[0];

    // 出力ファイルの拡張子は「.gz」
    string outFile = Path.GetFileName(inFile) + ".gz";

    int num;
    byte[] buf = new byte[1024]; // 1Kbytesずつ処理する

    FileStream inStream // 入力ストリーム
      = new FileStream(inFile, FileMode.Open, FileAccess.Read);

    FileStream outStream // 出力ストリーム
      = new FileStream(outFile, FileMode.Create);

    GZipStream compStream // 圧縮ストリーム
      = new GZipStream(
        outStream,  // 出力先となるストリームを指定
        CompressionMode.Compress); // 圧縮を指定

    using (inStream)
    using (outStream)
    using (compStream) {
      while ((num = inStream.Read(buf, 0, buf.Length)) > 0) {
        compStream.Write(buf, 0, num);
      }
    }
  }
}

// コンパイル方法:csc gzcomp.cs
// 使用方法:gzcomp <圧縮したいファイル>
GZIP形式でファイルの圧縮を行うC#のサンプル・プログラム(gzcomp.cs)

' gzcomp.vb

Imports System
Imports System.IO
Imports System.IO.Compression

Public Class CompressSample
  Shared Sub Main(ByVal args As String())

    Dim inFile As String = args(0)

    ' 出力ファイルの拡張子は「.gz」
    Dim outFile As String = Path.GetFileName(inFile) + ".gz"

    Dim num As Integer
    Dim buf(1024) As Byte ' 1Kbytesずつ処理する

    ' 入力ストリーム
    Dim inStream As New FileStream _
       (inFile, FileMode.Open, FileAccess.Read)

    ' 出力ストリーム
    Dim outStream As New FileStream _
      (outFile, FileMode.Create)

    ' 圧縮ストリーム
    Dim compStream As New GZipStream _
      (outStream, CompressionMode.Compress)

    Using inStream
    Using outStream
    Using compStream
      Do
        num = inStream.Read(buf, 0, buf.Length)
        If num <= 0 Then Exit Do
        compStream.Write(buf, 0, num)
      Loop
    End Using
    End Using
    End Using
  End Sub
End Class

' コンパイル方法:vbc gzcomp.vb
' 使用方法:gzcomp <圧縮したいファイル>
GZIP形式でファイルの圧縮を行うVBのサンプル・プログラム(gzcomp.vb)

 プログラムでは、作成している3つのストリームに対してusingステートメントを使用することにより、確実なリソースの解放(Disposeメソッドの呼び出し)を行っている。

ファイルを解凍するサンプル・プログラム

 続いてはGZIP形式で圧縮されたファイルの解凍を行うサンプル・プログラムを示す。このプログラムは、実行時に指定された圧縮ファイル(.gzファイル)を元のファイルに解凍する。解凍により作成されるファイルの名前は、単純に入力ファイル名から「.gz」を取ったものとなる(そのようなファイルがすでに存在していても上書きする)。

 このプログラムでは、入力元となるファイル・ストリームをセットした解凍ストリーム(GZipStreamオブジェクト)からデータを読み出し、それを出力ファイル用のファイル・ストリームに書き込んでいる。

// gzdecomp.cs

using System;
using System.IO;
using System.IO.Compression;

public class DecompressSample {
  static void Main(string[] args) {

    string inFile = args[0];

    // 入力ファイルは.gzファイルのみ有効
    if (!inFile.ToLower().EndsWith(".gz")) {
      return;
    }

    // ファイル名末尾の「.gz」を削除
    string outFile = inFile.Substring(0, inFile.Length - 3);

    int num;
    byte[] buf = new byte[1024]; // 1Kbytesずつ処理する

    FileStream inStream // 入力ストリーム
      = new FileStream(inFile, FileMode.Open, FileAccess.Read);

    GZipStream decompStream // 解凍ストリーム
      = new GZipStream(
        inStream, // 入力元となるストリームを指定
        CompressionMode.Decompress); // 解凍(圧縮解除)を指定

    FileStream outStream // 出力ストリーム
      = new FileStream(outFile, FileMode.Create);

    using (inStream)
    using (outStream)
    using (decompStream) {
      while ((num = decompStream.Read(buf, 0, buf.Length)) > 0) {
        outStream.Write(buf, 0, num);
      }
    }
  }
}

// コンパイル方法:csc gzdecomp.cs
// 使用方法:gzdecomp <解凍したい.gzファイル>
GZIP形式ファイルの解凍を行うC#のサンプル・プログラム(gzdecomp.cs)

' gzdecomp.vb

Imports System
Imports System.IO
Imports System.IO.Compression

Public Class DecompressSample
  Shared Sub Main(ByVal args As String())

    Dim inFile As String = args(0)

    ' 入力ファイルは.gzファイルのみ有効
    If Not inFile.ToLower().EndsWith(".gz")
      Return
    End If

    ' ファイル名末尾の「.gz」を削除
    Dim outFile As String = inFile.Substring(0, inFile.Length - 3)

    Dim num As Integer
    Dim buf(1024) As Byte ' 1Kbytesずつ処理する

    ' 入力ストリーム
    Dim inStream As New FileStream _
       (inFile, FileMode.Open, FileAccess.Read)

    ' 解凍ストリーム
    Dim decompStream As New GZipStream _
      (inStream, CompressionMode.Decompress)

    ' 出力ストリーム
    Dim outStream As New FileStream _
      (outFile, FileMode.Create)

    Using inStream
    Using outStream
    Using decompStream
      Do
        num = decompStream.Read(buf, 0, buf.Length)
        If num <= 0 Then Exit Do
        outStream.Write(buf, 0, num)
      Loop
    End Using
    End Using
    End Using
  End Sub
End Class

' コンパイル方法:vbc gzdecomp.vb
' 使用方法:gzdecomp <解凍したい.gzファイル>
GZIP形式ファイルの解凍を行うVBのサンプル・プログラム(gzdecomp.vb)

圧縮後のファイル・サイズ

 参考までに、テキスト・ファイル(上記サンプル・プログラムのgzcomp.cs)とバイナリ・ファイル(gzcomp.csをコンパイルして作成したgzcomp.exe)を、上記サンプル・プログラムおよび、ほかのいくつかの圧縮方式で圧縮したときのファイル・サイズを示す。ZIP形式およびRAR形式での圧縮についてはWinRARを用いている。

圧縮方式 圧縮後のサイズ(bytes) 圧縮率(%)
(未圧縮) 960 -
GZIP(本稿のサンプル・プログラム) 668 70
ZIP(圧縮方法:標準) 636 66
RAR(圧縮方法:標準) 616 64
RAR(圧縮方法:最高) 536 56
テキスト・ファイル(gzcomp.cs)の圧縮結果

圧縮方式 圧縮後のサイズ(bytes) 圧縮率(%)
(未圧縮) 3584 -
GZIP(本稿のサンプル・プログラム) 1767 49
ZIP(圧縮方法:標準) 1437 40
RAR(圧縮方法:標準) 1409 39
RAR(圧縮方法:最高) 1311 37
バイナリ・ファイル(gzcomp.exe)の圧縮結果

 これらの結果からも分かるように、GZIP形式はほかの一般的な圧縮方式と比べるとそれほど圧縮率は高くない。End of Article

利用可能バージョン:.NET Framework 2.0のみ
カテゴリ:クラス・ライブラリ 処理対象:ディレクトリ&ファイル
使用ライブラリ:GZipStreamクラス(System.IO.Compression名前空間)
使用ライブラリ:CompressionMode列挙体(System.IO.Compression名前空間)

この記事と関連性の高い別の.NET TIPS
HTTP圧縮を使用してWebページを取得するには?
[ASP.NET]動的に圧縮ファイルを生成するには?
このリストは、(株)デジタルアドバンテージが開発した
自動関連記事探索システム Jigsaw(ジグソー) により自動抽出したものです。
generated by

「.NET TIPS」


Insider.NET フォーラム 新着記事
  • 第2回 簡潔なコーディングのために (2017/7/26)
     ラムダ式で記述できるメンバの増加、throw式、out変数、タプルなど、C# 7には以前よりもコードを簡潔に記述できるような機能が導入されている
  • 第1回 Visual Studio Codeデバッグの基礎知識 (2017/7/21)
     Node.jsプログラムをデバッグしながら、Visual Studio Codeに統合されているデバッグ機能の基本の「キ」をマスターしよう
  • 第1回 明瞭なコーディングのために (2017/7/19)
     C# 7で追加された新機能の中から、「数値リテラル構文の改善」と「ローカル関数」を紹介する。これらは分かりやすいコードを記述するのに使える
  • Presentation Translator (2017/7/18)
     Presentation TranslatorはPowerPoint用のアドイン。プレゼンテーション時の字幕の付加や、多言語での質疑応答、スライドの翻訳を行える
@ITメールマガジン 新着情報やスタッフのコラムがメールで届きます(無料)

注目のテーマ

Insider.NET 記事ランキング

本日 月間