シェルのパイプとリダイレクトを活用する

文:Vincent Danen(TechRepublic) 翻訳校正:原井彰弘
2008-02-15 09:00:00
  • このエントリーをはてなブックマークに追加

 多くの人は、コマンドラインのコンピュータは過去のものだと思っている。しかし、コマンドラインでは非常に興味深いことも行えるのだ。Linuxのコマンドラインに慣れて、それを心地よく感じるようになると、美しいGUIと今はやりの魅力的なエフェクトでは得られない決定的なアドバンテージを得ることができるのである。

 そのようなアドバンテージの中に、パイプとリダイレクトがある。パイプとリダイレクトを利用すれば、複数のプログラムを「連鎖」させて非常に強力なコマンドを作成できるのだ。コマンドラインのプログラムは、その多くで異なるモードでの操作が行えるようになっている。多くのプログラムではファイルのデータを読み書きすることが可能であるが、その一方でほとんどのプログラムでは標準入力や標準出力も利用できるのである。すると、あるプログラムの出力を他のプログラムの入力として直接用いることが可能になる。さらに、2つ目のプログラムの出力を受け取り、さらにほかのプログラムの入力にリダイレクトを行ったり、ファイルにリダイレクトしたりすることもできるのだ。

 実は、多くのプログラムでは2つのモードで出力が行われる。標準出力(stdout)と標準エラー出力(stderr)だ。これらは異なる出力ストリームであり、はっきりと区別されている。そのため、あるプログラムのstderrを標準入力(stdin)と同様の「ストリーム」にリダイレクトしたり、異なる場所にリダイレクトしたりすることが可能なのだ。

 たとえば、psプログラムの出力をファイルにリダイレクトするには、以下のように記述する。

$ ps ax > output.txt

 また、2つの別々のファイルをすでにデータが含まれている1つのファイルにマージしたい場合は、catコマンドとリダイレクトを用いて以下のように記述できる。

$ cat 1.txt 2.txt >> 3.txt

 「>」を単独で用いると、出力はファイルにリダイレクトされるものの、ファイルがすでに存在した場合はその内容を上書きしてしまう。一方、2つ重ねて「>>」とした場合は、出力は同様にファイルへリダイレクトされるものの、ファイルがすでに存在した場合には、出力は既存の内容に追記される。このとき、ファイルが存在しない場合は新しく作成される。

 デフォルトでは、リダイレクトはstdoutに対して働き、stderrは一般的には画面に表示される。もし、stderrをstdoutと同じ「ストリーム」にリダイレクトしたければ、以下のようにすればよい。

$ strace ps ax > output.txt 2>&1

 ここで登場したstraceは変わったプログラムである。straceのstdoutには実際のプログラムの出力が出力されるものの、stderrにはトレース情報がすべて出力されるのである。上記のコマンドの場合には、straceはps axコマンドのシステムコールとシグナルをトレースし、stdoutとstderr双方をoutput.txtにリダイレクトする。これは、stderr(2という数値で表現されている)をstdout(&1で表現されている)のリダイレクト先にリダイレクトすることで実現されている。ここで、トレースの出力のみをファイルにリダイレクトして、psの出力はそのまま画面に表示したいような場合は、次のようにすればよい。

$ strace ps ax 2>strace.txt
  • 新着記事
  • 特集
  • ブログ