入力がある場合は、ジョブを実行する前にデータをフィルタリングする方が良いですかawk
、それともすべてのフィルタリングを実行する必要がありますかawk
?
たとえば、次の入力が与えられた場合:
$ echo "foo\nbar\nbaz"
foo
bar
baz
私は以下を実行する必要があります:
$ echo "foo\nbar\nbaz" | sed 1q | awk '{ print $0 " cats" }'
foo cats
または:
$ echo "foo\nbar\nbaz" | awk 'NR == 1 { print $0 " cats" }'
foo cats
- なぜこれを実行したいのですか?
- 他のツールを使用する必要がありますか?
- どの要素を考慮する必要がありますか?
- これらの要素をどのようにテストしますか?
答え1
この特別なケースでは、2番目のオプションはより良い選択です。
一般に、パイプ内のユーティリティの数を最小化する方が効率的です。sed
最初の例のように、不要なプロセスを分岐(開始)しないことをお勧めします。インターネットでは、苦情事例を見つけることは難しくありません。猫に役に立たない用途。
ほとんどの最新のUnixシリーズシステム*では、分岐は非常に効率的に行われますが、起動されるプロセスのサイズによって異なります。たとえば、perl
ORの開始はORよりはるかに遅いpython
です。sed
awk
ワンタイムコマンドの場合、これは重要ではありません。ただし、パイプラインがループ内にあり、複数回実行される場合、パイプラインから不要なプロセスを削除すると、全体の実行時間が大幅に短縮される可能性があります。
特定の問題
なぜこれを実行したいのですか?
どちらの構文にも慣れている場合は、最も使い慣れたツール/言語を使用してコードの読みやすさ(およびメンテナンス性)をさらに向上させることができます。
他のツールを使用する必要がありますか?
この特定のケースではそうは思いません。このタイプの作業に適したツールawk
です。sed
どの要素を考慮する必要がありますか?
複数のファイルを処理する必要がある場合(ループ内など)、速度/効率性が重要です。
大容量ファイルを頻繁に扱う場合は、コードの読みやすさがより重要になる可能性があります。
これらの要素をどのようにテストしますか?
time
組み込みのBashシェルまたはスタンドアロンランチャーとして提供されているこのユーティリティを使用して、さまざまなバージョンを分析できます。たとえば、2つのサンプルコマンドを実行すると、最初の例が2番目の例より0.012秒長くなることがわかります。
$ time echo "foo\nbar\nbaz" | sed 1q | awk '{ print $0 " cats" }'
foo\nbar\nbaz cats
real 0m0.056s
user 0m0.000s
sys 0m0.045s
$ time echo "foo\nbar\nbaz" | awk 'NR == 1 { print $0 " cats" }'
foo\nbar\nbaz cats
real 0m0.044s
user 0m0.000s
sys 0m0.031s
プロファイリングベンチマークはシステムの負荷やその他の制限要因の影響を受けるため、どのバージョンが他のバージョンよりも速いかを実際に把握するには、この操作を複数回繰り返す必要があります。
* MS Windowsの場合フォークはいコストが高いため、起動するプロセスの数を最小限に抑えると、Cygwin などの環境で実行する際に違いが発生します。
答え2
使用しても十分です。アッ(またはsed)これは簡単な状況のためのツールです。複数のツールを組み合わせることは、複雑すぎてしばしば重複する可能性があります。
echo -e "foo\nbar\nbaz" | awk 'NR==1{print $0" cats"}'
出力:
foo cats
どの要素を考慮する必要がありますか?
必要なテキスト処理には、さまざまなツールの組み合わせが必要であることを確認してください。それ以外の場合は、他のツール機能を使用してください。
入力文字列の最初の単語の前に特定の単語を追加する必要があるとします。これも簡単です。sedツール:
echo -e "foo\nbar\nbaz" | sed 's/^.*$/& cats/; 1q'
foo cats
echo -e
、e
フラグ「バックスラッシュエスケープ解析の有効化」
とにかく、入力テキストがどれくらい複雑なのか、テキスト処理ルールがどれだけ複雑なのかによって異なります。