2

この例は、bash を使用して Mac El Capitan でテストされました

main_script.sh:

output注: func_a と func_b は、ローカル変数が宣言されている行を除いて同一です。

func_a () {
    local output
    output="$(./external.sh some_function)"
    if [ $? -eq 0 ];then
        echo "A zero result ($?) -> $output <- end"
    else
        echo "A other result ($?) -> $output <- end"
    fi
}

func_b () {
    local output="$(./external.sh some_function)"
    if [ $? -eq 0 ];then
        echo "B zero result ($?) -> $output <- end"
    else
        echo "B other result ($?) -> $output <- end"
    fi
}

func_a
func_b

外部.sh:

some_function () {
    echo "this is the output"
    return 1
}

"$@"

main_script を実行すると、出力は次のようになります。

A other result (1) -> this is the output <- end
B zero result (0) -> this is the output <- end

コマンド置換と同じ行でローカル変数を宣言すると、どのような理由で結果に影響しますか? これはバグでしょうか、それとも何か不足していますか?

4

1 に答える 1

2

その理由は、$?inがコマンド置換 ( )の成功ではなくfunc_b、組み込みの成功を反映しているlocal$(...)ためです。

local割り当てが構文的に正しい場合、ビルトインは成功します- RHS でのコマンド置換が失敗するかどうかに関係なく。

declareこれはおよびビルトインにも同様に適用されることに注意してくださいexport

簡単な例で説明します。

declare output="$(false)"; echo $? # -> 0(!) - even though `false` obviously fails.

対照的に、組み込み関数が含まれていない場合(単純な変数割り当ての場合) 、コマンド置換の失敗次のように反映され$?ます。

output="$(false)"; echo $? # -> 1(!) - simple assignment; $(...) exit code is reported

この直感に反する動作の違いは、 //シェル構文の一部ではなく組み込みであるという事実によって説明されlocaldeclareexportます。

組み込み (組み込みコマンド) として、それらはcommandsのように扱われ、コマンドは独自の終了コードを介して成功/失敗を通知することが期待されます。上記のビルトインの場合、前述のように、構文的に正しい割り当ては成功と見なされます。つまり、何かを割り当てることができれば、RHS でコマンド置換が失敗したためにその何かがヌル文字列であっても、ビルトインは成功しました。

于 2016-06-19T19:58:54.237 に答える