コプロセス間で永続的なパイプラインを使用できるのと同じくらい、ダイアグラムが描くように、繰り返しフィードバックループが必ずしも必要だとは思いません。繰り返しになりますが、それほど大きな違いはないかもしれません-コプロセスで行を開くと、通常のスタイルループを実装できます。
そもそも、それがbc
コプロセスの最有力候補であるように見えます。bc
することができますdefine
あなたの擬似コードにするために、かなり多くのあなたが求める何ができる機能を。たとえば、これを行うためのいくつかの非常に単純な関数は次のようになります。
printf '%s()\n' b c a |
3<&0 <&- bc -l <<\IN <&3
a=1; b=0; c=0;
define a(){ "a="; return (a = c+1); }
define b(){ "b="; return (b = 3*a); }
define c(){ "c="; return (c = s(b)); }
IN
...印刷されます...
b=3
c=.14112000805986722210
a=1.14112000805986722210
しかし、もちろん、それは続きません。printf
のパイプを担当するサブシェルが終了するとすぐに(パイプへのprintf
書き込み直後a()\n
)、パイプは破棄され、bc
の入力が閉じて終了します。それは、それほど有用ではありません。
@derobertは、ユーティリティを使用して名前付きパイプファイルを作成することで、FIFOについて既に言及しています。これらは、システムカーネルがファイルシステムエントリを両端にリンクすることを除いて、基本的に単なるパイプです。これらは非常に便利ですが、ファイルシステムでスヌープされる危険を冒さずにパイプを使用できればさらに便利です。mkfifo
たまたま、シェルはこれをたくさん行います。プロセス置換を実装するシェルを使用する場合、永続的なパイプを取得する非常に簡単な手段があります。これは、通信可能なバックグラウンドプロセスに割り当てることができます。
ではbash
、たとえば、あなたがプロセス置換がどのように機能するかを見ることができます:
bash -cx ': <(:)'
+ : /dev/fd/63
あなたは本当にそれが代替品であることがわかります。シェルは、パイプへのリンクへのパスに対応する値を展開中に置き換えます。あなたはそれを利用することができます- 置換自体の中で実行されるプロセスと通信するためだけにそのパイプを使用するように制約される必要はありません...()
bash -c '
eval "exec 3<>"<(:) "4<>"<(:)
cat <&4 >&3 &
echo hey cat >&4
read hiback <&3
echo "$hiback" here'
...印刷する...
hey cat here
今、私は別のシェルが行うことを知っているコプロセスのさまざまな方法でものを-とにおける特定の構文があるというbash
ものを設定するための(おそらく1のためzsh
だけでなく)が -しかし、私はどのようにそれらのものの作品を知りません。私はちょうどあなたが両方でrigmaroleのすべてがなく、実質的に同じことを行うために上記の構文を使用することができることを知っているbash
とzsh
、あなたは非常に同じようなことを行うことができます- dash
とbusybox ash
ヒアドキュメントと同じ目的を達成するための理由(dash
とbusybox
DO here-他の2つのファイルのように、一時ファイルではなくパイプを使用したドキュメント)。
したがって、適用されるとbc
...
eval "exec 3<>"<(:) "4<>"<(:)
bc -l <<\INIT <&4 >&3 &
a=1; b=0; c=0;
define a(){ "a="; return (a = c+1); }
define b(){ "b="; return (b = 3*a); }
define c(){ "c="; return (c = s(b)); }
INIT
export BCOUT=3 BCIN=4 BCPID="$!"
...それは難しい部分です。そして、これは楽しい部分です...
set --
until [ "$#" -eq 10 ]
do printf '%s()\n' b c a >&"$BCIN"
set "$@" "$(head -n 3 <&"$BCOUT")"
done; printf %s\\n "$@"
...印刷する...
b=3
c=.14112000805986722210
a=1.14112000805986722210
#...24 more lines...
b=3.92307618030433853649
c=-.70433330413228041035
a=.29566669586771958965
...そして、それはまだ実行中です...
echo a >&"$BCIN"
read a <&"$BCOUT"
echo "$a"
... 関数を呼び出してそれをインクリメントして出力するbc
のa
ではなく、の最後の値を取得するだけa()
です...
.29566669586771958965
実際、私がそれを殺してそのIPCパイプを取り壊すまで、実行を続けます...
kill "$BCPID"; exec 3>&- 4>&-
unset BCPID BCIN BCOUT