web-dev-qa-db-ja.com

bashでは、forループのループ制御で整数変数を使用できますか?

次のbashスクリプトがあります。

#!/bin/bash

upperlim=10

for i in {0..10}
do
echo $i
done

for i in {0..$upperlim}
do
echo $i
done

最初のforループ(なしループコントロールの変数upperlim)は正常に動作しますが、2番目のforループ(withループ制御の変数upperlim)は行いません。 2番目のforループを変更して機能させる方法はありますか?御時間ありがとうございます。

70
Andrew

この理由は、bashで発生する順序です。ブレース展開before変数が展開されます。目標を達成するには、Cスタイルのforループを使用する必要があります。

upperlim=10

for ((i=0; i<=upperlim; i++)); do
   echo "$i"
done
67
jordanm

ビルトインだけを使用してスタイルでこれを完了するには、evalを使用する必要があります。

d=12

for i in `eval echo {0..$d}`
do
echo $i
done

しかし、seqの場合:

lowerlimit=0
upperlimit=12

for i in $(seq $lowerlimit $upperlimit)
do
echo $i
done

個人的には、seqの方が読みやすいと思います。

31
Jodie C

POSIXの方法

移植性を気にする場合は、 POSIX標準の例 を使用します。

_i=2
END=5
while [ $i -le $END ]; do
    echo $i
    i=$(($i+1))
done
_

出力:

_2
3
4
5
_

ではないものPOSIX:

Bashでは中括弧展開がパラメータ展開の前に発生するため、このアプローチは機能しません。前に変数を展開する必要があります。

eval で回避できます:

upperlim=10
eval '
        for i in {0..'"$upperlim"'}
        do
                echo $i
        done
'

Whileループ の場合:

upperlim=10
#with while
start=0
while [[ $start -le $upperlim ]]
do
    echo "$start"
    ((start = start + 1))
done

seqコマンド でも実行できます。

upperlim=10
#seq
for i in $(seq "$upperlim"); do
  echo "$i"
done

for i in {0..$upperlim}で実行する場合は、kornshellを使用する必要があります。例えば:

#!/bin/ksh
upperlim=10

for i in {0..$upperlim}
do
        echo $i
done
1