プロセスの置き換えによってパイプである/dev/fd/63というファイルが生成されるのはなぜですか?

プロセスの置き換えによってパイプである/dev/fd/63というファイルが生成されるのはなぜですか?

私はこの特定の例の文脈で名前付きパイプを理解しようとしています。

<(ls -l)端末に入力して出力を取得しましたbash: /dev/fd/63: Permission denied

と入力すると、cat <(ls -l)ディレクトリの内容を表示できます。置換catを使用すると、echo端末名(またはそうですか?)を取得できるようです。

echo <(ls -l)出力は次のように提供されます/dev/fd/63

また、この出力例は私には明確ではありません。

ls -l <(echo "Whatever")
lr-x------ 1 root root 64 Sep 17 13:18 /dev/fd/63 -> pipe:[48078752]

しかし、私が与えると、ls -l <()ディレクトリの内容が一覧表示されます。

名前付きパイプを使用するとどうなりますか?

ベストアンサー1

これにより、<(some_command)シェルは角括弧内のコマンドを実行し、内容全体をコマンドの標準出力に関連付けられたファイル記述子に置き換えます。/dev/fd/63ls呼び出しの出力を含むパイプも同様です。

これにより、行全体がパイプに置き換えられ、実際に実行できないコマンドで呼び出そうとするため、エラーが<(ls -l)発生します。Permission denied/dev/fd/63

2番目の例では、cat <(ls -l)になりますcat /dev/fd/63。 catが引数として提供されたファイルを読み取ると、内容が取得されます。echo一方、対応するパラメータを「現状のまま」出力するだけです。

最後のケースは、命令が<()なく、何もないものに置き換えられました。しかし、これはシェル間で一貫性がありません。 zsh ではまだパイプが表示されます (空であるにもかかわらず)。

一般化する: <(command)通常はファイルが必要ですが、コマンドの出力を使用できます。

編集する:〜のようにザイルズこれは、名前付きパイプではなく匿名パイプであることを指摘してください。主な違いは、プロセスが実行されている間に存在するのに対し、名前付きパイプ(例えば、で生成されるmkfifo)は、プロセスが接続されていない状態で変更されずに維持されることです。

おすすめ記事