関数はBashのサブプロセスとして実行されますか?


28

高度なバッシュ・スクリプトガイド例27-4、下から7番目のライン、私はこれを読みました:

関数はサブプロセスとして実行されます。

Bashでテストを行ったところ、上記の記述は間違っているようです。

このサイト、Bash Man、および私の検索エンジンでの検索では、何の効果もありません。

答えはありますか、説明したいですか?


12
前述のように、そのガイドは極端に誤解を招きます。代わりにWooledge Bash Guideをお勧めします。
ワイルドカード

回答:


36

高度なバッシュ・スクリプティングガイドは、常に信頼性がなく、そのサンプルスクリプトは時代遅れ含んな使用など、実践効果的に廃止予定のコマンド置換のためにバッククォートを、すなわち、`command`ではなく$(command)

この特定のケースでは、それは露骨に間違っています。

(標準)Bashマニュアルのシェル関数のセクションでは、

シェル関数は、現在のシェルコンテキストで実行されます。それらを解釈するための新しいプロセスは作成されません。


10
「高度なBashスクリプトガイドは一般に信頼性が低い」 非常に正しい。
John1024

1
最初の文をサポートするための参照を提供できますか?
ウィルヴーデン

5
@WillVousden参照は次のようになりますか?ガイドの技術的な不足の例の束?bashコミュニティの専門家が以前は信頼できないと指摘したドキュメントですか?bashに金のバッジが付いているstackoverflowメンバーがコメントで同意した場合、それは役に立ちますか?:p
小次郎

3
@WillVousdenあなたが望むものは、それ自体が信頼できる形で存在するとは思いません。メンデルクーパーは過去にガイドの問題を更新および修正しましたが、パブリックバグトラッカーまたはエラッタのリストはありません。(おそらくそれが、私ができる最もひどい声明です。)だから、私たちができることは、(知覚または現実の)欠陥を見つけたとき、著者にメールを送って、最善を期待することです。
小次郎

3
あなたがしたい場合@WillVousden、... 歴史 freenodeのの#bashチャネルにおけるコンセンサスはABSを回避すべきであるとされているどのくらいのを、見wooledge.org/~greybot/meta/absを - 2番目のフィールドを各行にはタイムスタンプで、最初はユーザー名です。問題のユーザー名は非常に尊敬されている個人であるという主張で十分であることを願っています。
チャールズダフィー

32

中括弧関数は、独自のサブシェルが必要でない限り、呼び出し元のシェルプロセス内で実行されます。

  • バックグラウンドで実行すると &
  • パイプラインでリンクとして実行するとき

リダイレクトまたは追加の環境。変数は新しいサブシェルを強制しません:

hw(){
    echo hello world from $BASHPID
    echo var=$var
} 
var=42 hw >&2
echo $BASHPID  #unexports var=42 and restores stdout here

カーリーの代わりに括弧で関数を定義する場合:

hw()(
  echo hello world from $BASHPID
)
hw 
echo $BASHPID

常に新しいプロセスで実行されます。

また、コマンド置換$()は常にbashでプロセスを作成します(ただし、内部で組み込みコマンドを実行する場合はkshでは作成されません)。


f() (...)許可されるとは知りませんでした。{...}および以外に他の定義はあり(...)ますか?Bashでは、私はまだ他の人には興味がありません。
トマス

1
@tomas function hw { echo hello world; } 構文を使用できます(()入力する必要はなくfunction、最後の直後}または)inのようにリダイレクトを指定できますhw(){ echo error; } >&2。それについてです。
PSkocik

2
これは私がすぐに考えた答えであり、絶対に正しいです。正解として投票する必要があります。f()(...)常に独自のシェルを実行しますが、実行しf(){...}ません。
-rexkogitans

11
NB bash関数は任意の複合コマンドを受け入れるためfoo() [[ x = x ]]、有効な関数定義も同様です。ただし、関数を見てみると、type fooこれはまだの構文糖衣であることがわかりますfoo() { [[ x = x ]]; }。同じことがサブシェル機能の真である:bar() ( : )なりbar() { ( : ); }
小次郎

1
@kojiro nice +1。それを知らなかった
PSkocik

9

その例からの問題のコマンドは次のようになります。

echo ${arrayZ[@]/%e/$(replacement)}

後の例では次のように述べています。

#    $( ... ) is command substitution.
#    A function runs as a sub-process.

ABS Guideに慈善的であるように、彼らが明らかに意図したことは、関数がコマンド置換内で実行され、コマンド置換内のコマンドがサブシェルで実行されることです。


それは非常に紛らわしいです。あなたの解釈をありがとう。
トマス

5
@tomas 「非常に誤解を招く。」 はい、非常に。ABSガイドとは対照的に、GregのWikiは高度なbash情報の優れた情報源です。
John1024

1
乾杯。これについてのあなたの意見:wiki.bash-hackers.org/start
トマス

@tomas私はそれについての直接の知識を持っていません。
John1024

2
@tomas、... bash-hackers wikiに関する私自身の意見は、それが優れたソースであるということです。Wooledge wikiほど包括的なものではありませんが、正確で正確に記述される傾向があります。
チャールズダフィー
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.