bashシェルと環境変数を学んでいます。
echo a envをテストしました。 varは引用符なしで引用符で囲みます(私はこれを端末に入れました)。
user@pc:~$ echo "$BASE_DEPENDENCIES"
build-essential \
cmake \
debhelper \
mesa-utils \
cppcheck \
xsltproc \
python-psutil \
python \
bc \
netcat-openbsd \
gnupg2 \
net-tools \
locales
user@pc:~$ echo $BASE_DEPENDENCIES
build-essential \ cmake \ debhelper \ mesa-utils \ cppcheck \ xsltproc \ python-psutil \ python \ bc \ netcat-openbsd \ gnupg2 \ net-tools \ locales
最初の行には新しい行とスペースがあります。 2番目には1行しかありません。
なぜこれが起こるのですか?
ちなみに、私のシステムはUbuntu 17.04です。
答え1
一つある拡張順序bashが入力したときの作業:
拡張順序は、中かっこ拡張、引数と変数拡張、算術拡張、コマンド置換(左から右へ)です。
引用されていないバージョンは次のものを受け入れます。噴射(私のハイライト):
パラメータ拡張、コマンド置換、および算術拡張のシェルスキャン結果二重引用符内には表示されません。単語の分割に使用されます。
...デフォルトはです。これは複数の単語になるという$IFS
意味です。build-essential \(newline)(other spaces)cmake ...
build-essential
\
cmake
- ...
...改行文字と各空白文字内のすべての文字を効果的に削除します。
変数を引用すると、何よりも単語の分割が防止されます。
追加資料:
答え2
シェルは、1つ以上のスペース(つまり、スペース、タブ、改行)文字を使用してコマンドから引数を区切ります。引用符が含まれていない場合、値は$BASE_DEPENDENCIES
N引数に拡張されます。 echo
すべてのパラメータを取得し、単一のスペースで区切られた各パラメータを印刷すると、次の結果が得られます。
build-essential<space>\<space>cmake<space>\...
引用符はスペースの区切りを無視します。引用符内のすべての内容は単一引数として渡されます。この場合、gets値には$BASE_DEPENDENCIES
1つの引数が渡されますecho
。 echo
次に、提供された引数の1つを印刷します(スペース、改行などはそのままにします)。
よりよく理解するには、次の簡単なシェル関数を検討してください。この場合、コマンドと同じです。
foo() {
for i in "${@}"; do
echo "->'${i}'"
done
}
次のような変数があるとしましょう。
x=" 1 2 3 4 "
引用符がない場合は、4つのパラメータを取得します。
$ foo $x
->'1'
->'2'
->'3'
->'4'
引用符を使用すると、1つだけを取得できます。
$ foo "$x"
->' 1 2 3 4 '
答え3
引用すると空白が保存されるからです。これを以下と比較してみてください。
# a=$(cal)
# echo $a
October 2017 Su Mo Tu We Th Fr Sa 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31
# echo "$a"
October 2017
Su Mo Tu We Th Fr Sa
1 2 3 4 5 6 7
8 9 10 11 12 13 14
15 16 17 18 19 20 21
22 23 24 25 26 27 28
29 30 31
まず、cal
コマンド出力がに保存されますa
。その後、引用符なしで引用符で印刷されます。ご覧のとおり、引用符はスペースを保持しますが、引用符はテキストを次のように区別しません。トークン、スペースで区切られます。