Это зависит от оболочки и не документировано AFAICS. В ksh
и bash
, в первом случае, foo
будет использоваться тот же stdin, что и bar
. Они будут бороться за выход echo
.
Так, например, в
$ seq 10000 | paste - <(tr 1 X)'
1 X
2 X042
3 X043
4 X044
5 X045
[...]
Вы видите свидетельство, которое paste
читает каждый второй блок текста из seq
выходных данных, в то время как tr
читает другие.
С помощью zsh
он получает внешний stdin (если только он не является терминалом и оболочка не является интерактивной, и в этом случае она перенаправляется /dev/null
). ksh
(где он возник), zsh
и bash
являются единственными Bourne-подобными оболочками с поддержкой процесса замены AFAIK.
В echo "bla" | bar < <(foo)
, заметим , что bar
STDIN «S будет труба подается на выходной сигнал foo
. Это хорошо определенное поведение. В этом случае, похоже, что foo
stdin - это канал, которым питаются echo
все ksh
, zsh
и bash
.
Если вы хотите иметь согласованное поведение во всех трех оболочках и быть ориентированными на будущее, поскольку поведение может измениться, поскольку оно не задокументировано, я написал бы это:
echo bla | { bar <(foo); }
Чтобы быть уверенным, что foo
stdin - это еще и канал echo
(хотя я не понимаю, почему вы хотите это сделать). Или:
echo bla | bar <(foo < /dev/null)
Для того, чтобы убедиться , что foo
ничего не читать из трубы с echo
. Или:
{ echo bla | bar 3<&- <(foo <&3); } 3<&0
Иметь foo
's stdin' внешний stdin, как в текущих версиях zsh
.