私は初めてLinuxシェルスクリプトに触れ、次のスクリプトを書いています。
スクリプトは正常に実行されますが、プログラムが完了してプログラムが完了したというメッセージが表示された後にコマンドラインプロンプトを表示するには、キーボードで手動で[ENTER]を押す必要があります。私のスクリプトはなぜこのように動作しますか?
サブプロセスが完了し、スクリプトエコープログラムが完了したときに制御がコマンドラインに戻り、コマンドラインプロンプトを表示するために何もする必要がないようにするにはどうすればよいですか。
#!/bin/ksh
echo "program running..."
funcall(){
nohup <<command_name>> $program >/dev/null 2>&1
pid = $!
wait pid
echo "program completed..."
exit
}
fork(){
funcall &
}
fork
答え1
分岐したプロセスがそれ自体を待つのは非常にまれです。
制御フローは次のようにする必要があります。
- フォークプロセス
- 子プロセスはそのタスクを実行します。
- 両親はやるべきことをして待つ
これは次のように翻訳されます。
#!/bin/ksh
echo "program running..."
funcall () {
nohup some_command "$program" >/dev/null 2>&1
echo "program completed..."
}
fork () {
funcall &
}
fork
child_pid="$!"
wait "$child_pid"
この場合、関数の実行中は何もしないため、呼び出しの背景とfuncall
関数呼び出しが返されるのを待つことは完全に不要ですfork
。funcall
コードが行うのは、バックグラウンドでサブシェルを実行し、すぐに親シェルに制御を返すことです。スクリプトの出力により、プロンプトが少し混乱することがあります。
スクリプトにはいくつかのエラーもあります。
pid
変数として使用されますが、必要です$pid
。- 割り当てられたターゲット
pid
の周りにスペースを入れないでください=
。
またexit
必要ありません。
あなたの要件を満たす簡単なスクリプトは次のとおりです。
#!/bin/ksh
echo "program running..."
nohup some_command "$program" >/dev/null 2>&1
echo "program completed..."
答え2
プロセスが完了すると、すでにコマンドプロンプトにありますが、プロンプト自体はスクリプトの背景部分の出力によって隠されます。
Enterキーを押すと、コマンドラインに入力したコマンド(何もない場合があります)が実行され、「回復プロンプト」のように表示されるプロンプトが再印刷されます。
間違った出力後に画面をクリーンアップするには、Ctrl-Lを押します。
答え3
コードを次から変更してください。 funcall&
到着funcall
。funcall
バックグラウンドで実行しているため、親プロセスはつまり。あなたのスクリプト子プロセスが完了するのを待っています。
funcall をフォアグラウンドで実行すると、プログラムは正常に終了します。