ある時点でフォークしたいスクリプトがあるので、同じスクリプトの2つのコピーが実行されます。
たとえば、 、次のbashスクリプトを存在させたい:
echo $$ do_fork() echo $$
このbashスクリプトが本当に存在する場合、期待される出力は次のようになります。
<ProcessA PID> <ProcessB PID> <ProcessA PID>
または
<ProcessA PID> <ProcessA PID> <ProcessB PID>
これを取得するために「do_fork()」の代わりに配置できるものはありますかある種の出力、またはbashスクリプトにCのようなフォークを実行させるには?
回答
はい。フォークのスペルは&
:
echo child & echo parent
混乱するかもしれませんが、$$
はシェルプロセスのPIDではなく、元のシェルプロセスのPIDです。このようにすることのポイントは、$$
は、シェルスクリプトの特定のインスタンスの一意の識別子です。スクリプトの実行中には変更されず、同時に実行されている他の$$
とは異なります。脚本。シェルプロセスの実際のPIDを取得する1つの方法は、sh -c "echo $PPID"
です。
シェルの制御フローはCと同じではありません。 “d write
first(); fork(); second(); third();
シェルに相当するものは
after_fork () { second; third; } first; after_fork & after_fork
単純なシェル形式first; child & parent
は通常のCイディオムに対応します
first(); if (fork()) parent(); else child();
&
および$$
は、すべてのBourneスタイルのシェルと(t)cshに存在し、このように動作します。$PPID
は元のBourneには存在しませんでした。シェルですが、POSIXにあります(つまり、ash、bash、ksh、zshなどにあります)。
コメント
回答
はい、サブシェルと呼ばれます。括弧内のシェルコードはサブシェル(フォーク)。ただし、通常、最初のシェルは子が完了するのを待ちます。&
ターミネーターを使用して非同期にすることができます。次のような動作を確認してください。
#!/bin/bash (sleep 2; echo "subsh 1")& echo "topsh"
$ bash subsh.sh
コメント
- 括弧はサブシェルを作成します、ただし、'のフォーク+待機。
&
はフォークのみです。子プロセスで複数のパイプラインを実行する場合は、 '中括弧(子プロセスを作成せずにグループ化を実行する)を使用するのに十分です:{ sleep 2; echo child; } &
回答
ネイティブはありませんこれを行うbash(または私の知る限り、他の典型的な* nixシェル)の方法。 「非同期で他のことを行うforkプロセスを生成する方法はたくさんありますが、fork()システムコールの正確なセマンティクスに従うものはないと思います。
一般的なアプローチはトップレベルのスクリプトで、必要な作業だけを実行するヘルパーを生成する必要があります。$0 $@ &
などを実行する場合は、最初からやり直す必要があります。どういうわけかそれを理解してください。
私は実際に、それを行うためのいくつかの賢い方法を考え始めています…
しかし、、私の脳がそれに夢中になりすぎる前に、かなり良いルールは、「シェルで何かを書き込もうとしていて、それが巧妙なトリックがたくさんあり、「より多くの言語機能が必要です。実際のプログラミング言語に切り替える時間」。
コメント
- 要点はよく理解されていますが、bash 'の構文は間違いなく難しく、 ' PerlまたはPythonのより洗練されたデータ構造と機能が欠けているため、bashはそのドメインで得られるのと同じくらいリアルです。これはドメイン固有言語であり、多くの場合、Pythonなどよりもさらに優れている(より簡潔で単純な)と主張します。たくさんのシステムを管理していて、Pythonを知らないでしょうか?はい。あなたはそれをすることができて、bash [プログラミング]のなめを知らないのですか? '試してみたいとは思いません。 30年間のシェルプログラミングの後、私はそれを'できるだけリアルに伝えます。はい、私はPythonを話します。ただし、'若者を混乱させないでください。
- そうは言っても、技術的にはこの回答の方が好きです。 " & "がユーザーへの答えであると言うこと'の質問、"ある時点でフォークして、同じスクリプトの2つのコピーが実行されている"は私の混乱する心。 bashのマニュアルによると、" & "が行うことは" …サブシェルのバックグラウンドで[given]コマンドを実行します。"コマンドを終了する必要があり、フォークが含まれます(技術的には、Linuxではclone())ですが、その時点では同じスクリプトの2つのコピーが実行されていません。
&
はフォークですが、'実行者は関与していません。Fork+ execは外部コマンドを起動するときです。exec
はありませんが、2つの言語の制御フローは異なります。&
は、指定されたコマンドが実行されるサブシェルを開始します。フォーク+幹部。 '実行するコマンドがない状態で&
を配置することはできません。