web-dev-qa-db-ja.com

非常に大きな(100G)ファイルを圧縮する時間

多くの非常に大きなファイル(80ギガバイト)を圧縮しなければならないことに気付き、システムの速度(不足)に驚いています。変換速度は約500 MB /分です。 topを使用すると、単一のCPUを約100%使用しているようです。

tarファイルの作成(80Gファイルの作成方法)には数分(おそらく5または10)しかかかりませんが、2時間以上経過したので、ディスクアクセス速度は(単なる)ではないと確信しています。私の単純なgzipコマンドはまだ実行されていません。

要約すれば:

tar -cvf myStuff.tar myDir/*

87 Gのtarファイルを作成するために5分未満かかりました

gzip myStuff.tar

2時間10分かかり、55G Zipファイルが作成されました。

私の質問:これは正常ですか? gzipには、速度を上げるための特定のオプションがありますか?コマンドを連結してtar -cvfzを使用する方が速いでしょうか? pigz- GZipの並列実装 -への参照を見ましたが、残念ながら、使用しているマシンにソフトウェアをインストールできないため、これは私にとっては選択肢ではありません。たとえば この前の質問 を参照してください。

私はこれらのオプションのいくつかを自分で試して時間を計るつもりです-しかし、私はオプションの「魔法の組み合わせ」をヒットしない可能性が非常に高いです。このサイトの誰かが物事をスピードアップするための正しいトリックを知っていることを願っています。

他の試験の結果が利用可能になったら、この質問を更新します。ただし、特に優れたトリックが利用できる人がいれば、本当に感謝します。たぶん、gzipは私が気付いたよりも処理時間が長くかかるだけかもしれません...

[〜#〜]更新[〜#〜]

約束どおり、以下に示すトリックを試しました。圧縮量を変更し、ファイルの宛先を変更します。約4.1GBのtarに対して次の結果が得られました。

flag    user      system   size    sameDisk
-1     189.77s    13.64s  2.786G     +7.2s 
-2     197.20s    12.88s  2.776G     +3.4s
-3     207.03s    10.49s  2.739G     +1.2s
-4     223.28s    13.73s  2.735G     +0.9s
-5     237.79s     9.28s  2.704G     -0.4s
-6     271.69s    14.56s  2.700G     +1.4s
-7     307.70s    10.97s  2.699G     +0.9s
-8     528.66s    10.51s  2.698G     -6.3s
-9     722.61s    12.24s  2.698G     -4.0s

したがって、はい、フラグをデフォルトの-6から最速-1に変更すると、Zipファイルのサイズがほとんど(データの場合)変更されず、30%高速化されます。同じディスクを使用していても別のディスクを使用していても、本質的に違いはありません(統計的な有意性を得るために、これを複数回実行する必要があります)。

興味があれば、次の2つのスクリプトを使用してこれらのタイミングベンチマークを生成しました。

#!/bin/bash
# compare compression speeds with different options
sameDisk='./'
otherDisk='/tmp/'
sourceDir='/dirToCompress'
logFile='./timerOutput'
rm $logFile

for i in {1..9}
  do  /usr/bin/time -a --output=timerOutput ./compressWith $sourceDir $i $sameDisk $logFile
  do  /usr/bin/time -a --output=timerOutput ./compressWith $sourceDir $i $otherDisk $logFile
done

そして、2番目のスクリプト(compressWith):

#!/bin/bash
# use: compressWith sourceDir compressionFlag destinationDisk logFile
echo "compressing $1 to $3 with setting $2" >> $4
tar -c $1 | gzip -$2 > $3test-$2.tar.gz

注意すべき3つのこと:

  1. timeの組み込みコマンドにはGNUコマンドよりもはるかに少ないオプションがあるため、bashではなく/usr/bin/timeを使用します。
  2. --formatオプションを使用する手間は省きましたが、ログファイルが読みやすくなります。
  3. timeはパイプシーケンスの最初のコマンドでのみ動作するようだったので、スクリプト内のスクリプトを使用しました(そのため、単一のコマンドのように見せました...)。

このすべてを学んだことで、私の結論は

  1. -1フラグでスピードアップ(受け入れられた回答)
  2. ディスクから読み取るよりもはるかに多くの時間がデータの圧縮に費やされます
  3. より高速な圧縮ソフトウェアに投資してください(pigzは良い選択のようです)。
  4. 圧縮するファイルが複数ある場合は、各gzipコマンドを独自のスレッドに配置して、利用可能なCPUをより多く使用できます(貧乏人のpigz

このすべてを学ぶのを助けてくれたみんなに感謝します!

30
Floris

--fast--bestまたは-#を使用してgzipの速度を変更できます。ここで、#は1から9までの数値です(1は最も高速ですが、圧縮率は低く、9は最も低速ですが圧縮率は高くなります)。デフォルトでは、gzipはレベル6で実行されます。

29
robingrindrod

Tarがgzipに比べて時間がかからない理由は、ファイルを単一のファイルにコピーする際の計算上のオーバーヘッドが非常に少ないためです(これが機能です)。一方、gzipは実際には圧縮アルゴリズムを使用してtarファイルを圧縮しています。

問題は、gzipが(あなたが発見したように)単一のスレッドに制限されていることです。

pigz と入力すると、複数のスレッドを使用して圧縮を実行できます。これを使用する方法の例は次のとおりです。

tar -c --use-compress-program=pigz -f tar.file dir_to_Zip

姉妹サイト に--use-compress-programオプションのニースで簡潔な要約があります。

29
Steve Gore

1つのCPUを約100%使用しているようです。

これは、I/Oパフォーマンスの問題はないが、圧縮は1つのスレッドのみを使用していることを意味します(これはgzipの場合です)。

他のツールをインストールするために必要なアクセス/同意を達成できた場合、7ZipはマルチコアCPUを利用するために複数のスレッドもサポートしますが、それが独自のgzip形式に拡張されているかどうかはわかりません。

とりあえずgzipだけを使用することにこだわっており、複数のファイルを圧縮する必要がある場合は、それらを個別に圧縮してみてください。複数のプロセスを並行して実行することで、マルチコアCPUをより多く使用できます。 I/Oサブシステムの容量の近くに到達するとすぐに、ヘッドの動きの待ち時間が大きくなるため、I/Oサブシステムのパフォーマンスが急激に低下します(1つのプロセス/スレッドを使用している場合よりも低くなります)。ボトルネック。

4
David Spillett

次のコマンドに示すように、通常はより高速なパフォーマンスであるpigzでも使用可能なプロセスの数を活用できます。

tar cf-アーカイブするディレクトリ| pigz -0 -p大きな数値> mydir.tar.gz

例-tar cf-patha | pigz -0 -p 32> patha.tar.gz

-pは実行できるプロセスの数であるため、これはおそらく投稿で提案されている方法よりも高速です。私の個人的な経験では、アーカイブするディレクトリが多数の小さなファイルで構成されている場合、非常に大きな値を設定してもパフォーマンスに影響はありません。そうでない場合、考慮されるデフォルト値は8です。大きなファイルの場合、この値をシステムでサポートされるスレッドの総数として設定することをお勧めします。

32 CPUマシンの場合は、p = 32の値を設定する例が役立ちます。

0は、アーカイブを圧縮せず、速度を重視するため、pigz圧縮が最も高速であることを意味します。圧縮の場合、デフォルト値は6です。

1
Ankit Shah