回答:
あなたの主な質問に答えること${foo}は、「パラメータ拡張」と呼ばれます。正確には、$それ自体がパラメータ展開を開始します。これ{ }は実際にはPOSIX仕様によればオプションですが、変数名の終わりを示すのに役立ちます。
$ foo="bar"
$ echo $fooBaz ## fails, no variable named $fooBaz exists
$ echo ${foo}Baz ## works, $foo is expanded and the string Baz is appended
barBaz
基本的に、$fooかつ${foo}同一です。上記のような場合を除いて、または文字列操作を行っている場合は、まったく同じです。
ただし、実際にはどちらも使用しないでください。親指のルールは非常に少数の例外を除いて、あなたがすべき、ということです常に使用し"$foo"たり"${foo}"と、決して$fooまたは${foo}。split + glob演算子を呼び出さないように、常に変数を引用符で囲む必要があります(これについては後で詳しく説明します)。あなたは確かに望んでいない$foo$。決勝$は無関係です:
$ foo="bar"
$ echo "$foo$"
bar$
したがって、引用符で囲まれていない変数でも問題ない場合があります。
$ echo $foo
bar
これらは通常は行われず、実際に回避する必要があります。
$ if [ -n $foo ]; then echo empty; else echo "not empty"; fi ## fails
empty
$ if [ -n "$foo" ]; then echo empty; else echo "not empty"; fi ## works
not empty
括弧はここでも役に立たないことに注意してください:
$ if [ -n ${foo} ]; then echo empty; else echo "not empty"; fi ## fails
empty
$ if [ -n "${foo}" ]; then echo empty; else echo "not empty"; fi ## works
not empty
あなたが使用している場合$fooや${foo}、シェルがします分割(これは設定で変更することができ空白に変数に保存された値をIFSリストに何か他に変数を)してから、リストの各要素は、として扱われグロブパターンとに展開します一致するファイルまたはディレクトリ。これは、split + glob演算子として知られています。説明のために、2つのファイルを含むディレクトリを考えます。
$ ls -l
-rw-r--r-- 1 terdon terdon 0 Oct 9 18:16 file1
-rw-r--r-- 1 terdon terdon 0 Oct 9 18:16 file2
次に、変数をfoo *次のように設定します。
$ foo="foo *"
その名前のファイルが存在するかどうかを確認しようとするとどうなりますか?
$ if [ -e $foo ]; then echo "file exists"; else echo "no such file"; fi
file exists
変数はfooand に分割されました*。これ*は、任意の文字列に一致するワイルドカードであるため、シェルはfoo *exxists というファイルがあることを通知します。ただし、正しく引用すると、これは起こりません。
$ if [ -e "$foo" ]; then echo "file exists"; else echo "no such file"; fi
no such file
これはポイントを説明するための簡単な例でした。rm代わりに使用したと想像してみてくださいecho。
したがって、最初のルールは、常に変数を引用することです。あなたはどちらかを使用することができます"$foo"か"${foo}"が、いずれかの方法、それを引用します。変数を安全に使用する方法の詳細については、次の投稿をご覧ください。
$ var="foo *"が、そうすべきではありません$ foo="foo *"か?あなたはvarどこでも使用しません。
$最終的には使用しないでください!変数名の一部としてではなく、通常の文字として扱われます。