まず、シェルの<(command)
コマンド置換がどのように機能するかを見てみましょう。コマンドは、新しく作成されたパイプを指す出力で開始されます。次に、パイプはコマンドラインでファイル名として外部コマンドに渡されます。
例えば:
$ echo wc -w <(date)
wc -l /dev/fd/63
シェルがdate
パイプへの出力から開始し、/dev/fd/63
ファイル記述子 63 で新しいパイプを参照する疑似ファイルを実際のコマンド ライン引数として渡すことを示します。
Python で同じ動作を得るために、同じことを実装できます。
from subprocess import *
date = Popen(['date'], stdout=PIPE)
Popen(["wc", "-w", "/dev/fd/%d" % date.stdout.fileno()])
印刷する
6 /dev/fd/3
簡単にするためにクラスを書くことができます。これはwith
ステートメントを使用し、生成された各プロセスへの参照を一時的に保持します。そうしないと、プロセス オブジェクトがガベージ コレクションされたときにパイプが閉じられるためです。
from subprocess import *
class CommandSubstituter(object):
def __init__(self):
self._procs = []
def __enter__(self):
return self
def __exit__(self, *exc_info):
pass
def subst(self, *args, **kwargs):
proc = Popen(*args, stdout=PIPE, **kwargs)
self._procs.append(proc)
return "/dev/fd/%d" % proc.stdout.fileno()
with CommandSubstituter() as c:
Popen(['wc', '-l',
c.subst(['comm', '-12',
c.subst(['sort', 'file1.txt']),
c.subst(['sort', 'file2.txt'])])])