次のコードを変更して、zshで実行したときに$things
とそれらを1つずつ繰り返しますか?
things="one two"
for one_thing in $things; do
echo $one_thing
done
出力を次のようにします。
one
two
しかし、上に書いたように、それは出力します:
one two
(bashで上記のコードを実行したときに得られる動作を探しています)
Bourne Shellと互換性のある動作を確認するには、オプションSH_Word_SPLIT
を設定する必要があります。
setopt shwordsplit # this can be unset by saying: unsetopt shwordsplit
things="one two"
for one_thing in $things; do
echo $one_thing
done
生成するもの:
one
two
ただし、Word分割の生成には配列を使用することをお勧めします。
things=(one two)
for one_thing in $things; do
echo $one_thing
done
以下を参照することもできます。
z
変数展開フラグを使用して、変数でWord分割を実行できます。
things="one two"
for one_thing in ${(z)things}; do
echo $one_thing
done
これと他の変数フラグの詳細については、man zshexpn
の「Parameter Expansion Flags」を参照してください。
Bashの内部フィールドセパレーター(IFS)は\ x20(スペース)であると想定できます。これにより、次のことが可能になります。
#IFS=$'\x20'
#things=(one two) #array
things="one two" #string version
for thing in ${things[@]}
do
echo $thing
done
これを念頭に置いて、IFSを操作するだけでさまざまな方法でこれを実装できます。複数行の文字列でも。
Bourneシェル(sh、bash、zshなど)の間でも移植可能な別の方法:
things="one two"
for one_thing in $(echo $things); do
echo $one_thing
done
または、$things
を変数として定義する必要がない場合:
for one_thing in one two; do
echo $one_thing
done
for x in y z
を使用すると、単語のリストy, z
をループするようシェルに指示されます。
最初の例では、 コマンド置換 を使用して、文字列"one two"
を単語のリストone two
(引用符なし)に変換します。
2番目の例は、echo
なしの同じものです。
うまく理解できない例があります:
for one_thing in "one two"; do
echo $one_thing
done
引用符に注意してください。これは単に印刷されます
one two
引用符は、リストにone two
という単一の項目があることを意味するためです。