古典的な手法(メタ文字のエスケープ):
if [ \( "$g" -eq 1 -a "$c" = "123" \) -o \( "$g" -eq 2 -a "$c" = "456" \) ]
then echo abc
else echo efg
fi
への参照を$g二重引用符で囲みました。これは一般的には良い習慣です。優先順位ので厳密には、括弧は必要ありません-aとは-o、それは彼らがなくても修正します。
ことを注意-aして-oオペレーターがためにPOSIX仕様の一部であるtest別名、[主に(彼らはの一部であったため、後方互換性のために、test例えば、第7版UNIXの場合)が、彼らが明示的にPOSIXよる「旧式」としてマークされています。bashは(参照条件式を)のための古典とPOSIXの意味を先取りするようだ-aと、-o引数を取る独自の代替事業者と。
少し注意して、よりモダンな[[演算子を使用できますが、BashとKorn Shell(たとえば)のバージョンが同じである必要はないことに注意してください。
for g in 1 2 3
do
for c in 123 456 789
do
if [[ ( "$g" -eq 1 && "$c" = "123" ) || ( "$g" -eq 2 && "$c" = "456" ) ]]
then echo "g = $g; c = $c; true"
else echo "g = $g; c = $c; false"
fi
done
done
Mac OS XでBash 3.2.57を使用した実行例:
g = 1; c = 123; true
g = 1; c = 456; false
g = 1; c = 789; false
g = 2; c = 123; false
g = 2; c = 456; true
g = 2; c = 789; false
g = 3; c = 123; false
g = 3; c = 456; false
g = 3; c = 789; false
あなたには、変数を引用する必要はありません。[[あなたがそうであるように[、それは同じように別々のコマンドではないため[ですが。
古典的な質問ではないですか?
私はそう思っただろう。ただし、別の方法があります。
if [ "$g" -eq 1 -a "$c" = "123" ] || [ "$g" -eq 2 -a "$c" = "456" ]
then echo abc
else echo efg
fi
実際、autoconfツールまたは関連パッケージの「ポータブルシェル」のガイドラインを読んだ場合、この表記(「||」と「&&」を使用)が推奨されます。私はあなたがこれまでに行くことができると思います:
if [ "$g" -eq 1 ] && [ "$c" = "123" ]
then echo abc
elif [ "$g" -eq 2 ] && [ "$c" = "456" ]
then echo abc
else echo efg
fi
アクションがエコーと同じくらい簡単な場合、これは悪くありません。繰り返されるアクションブロックが複数行である場合、繰り返しが非常に面倒であり、以前のバージョンの1つが望ましいです。または、アクションを別のthenブロックで呼び出される関数にラップする必要があります。
test([)によって評価されます。シェルはの終了ステータスのみを評価します[。