如何在bash for循环中使用变量? 如果我只是使用标准for循环,它会做我期望的
for i in {0..3}
do
echo "do some stuff $i"
done
这很好用。它循环4次,0到3次,打印我的信息并将计数结束。
do some stuff 0
do some stuff 1
do some stuff 2
do some stuff 3
当我尝试使用以下for循环时,它似乎等于一个字符串,这不是我想要的。
length=3
for i in {0..$length}
do
echo "do something right $i"
done
输出:
do something right {0..3}
我试过
for i in {0.."$length"} and for i in {0..${length}} (both output was {0..3})
和
for i in {0..'$length'} (output was {0..$length})
他们都没有做我需要的事情。希望有人可以帮助我。提前感谢任何bash专家对for循环的帮助。
答案 0 :(得分:33)
一种方法是使用eval
:
for i in $( eval echo {0..$length} )
do
echo "do something right $i"
done
注意设置length=;ls
或length=; rm *
时会发生什么(尽管不要尝试后者)。
安全,使用seq
:
for i in $( seq 0 $length )
do
echo "do something right $i"
done
或者您可以使用c-style for循环,这也是安全的:
for (( i = 0; i <= $length; i++ ))
do
echo "do something right $i"
done
答案 1 :(得分:7)
在bash中,大括号扩展是第一个步骤,因此,$length
将不会被替换。
bash的联机帮助页明确指出:
序列表达式采用{x..y [.. incr]}形式,其中x和y 整数或单个字符 ......
有许多可能性,例如使用:
pax> for i in $(seq 0 $length) ; do echo $i ; done
0
1
2
3
虽然如果length
很大,这可能会给你一个大的命令行。
另一种选择是使用类C语法:
pax> for (( i = 0; i <= $length; i++ )) ; do echo $i; done
0
1
2
3
答案 2 :(得分:3)
大括号替换是在任何其他之前执行的,因此您需要使用eval
或
像seq
这样的第三方工具。
评估示例:
for i in `eval echo {0..$length}`; do echo $i; done
实际上可以在man bash
:
序列表达式采用{x..y [.. incr]},的形式,其中x和y是其中之一 整数或单个字符,incr是一个可选的增量,是一个整数。 [...]
在任何其他扩展之前执行大括号扩展,以及任何特殊字符 结果中保留了其他扩展。严格来说是文本。 Bash不对扩展的上下文应用任何语法解释 或大括号之间的文字。