目前正在开发以下版本的Bash:
GNU bash, version 4.2.46(1)-release (x86_64-redhat-linux-gnu)
我目前的剧本:
#!/usr/bin/env bash
function main() {
local commands=$@
for command in ${commands[@]} ; do
echo "command arg: $command"
done
}
if [[ "${BASH_SOURCE[0]}" == "$0" ]]; then
set -e
main $@
fi
简单来说,如果脚本被调用,这个脚本只会执行main
,类似于Python的if __name__ == '__main__'
约定。
在main
函数中,我只是循环遍历所有命令变量,但引用转义并不是按预期发生的:
$ tests/simple /bin/bash -c 'echo true'
command arg: /bin/bash
command arg: -c
command arg: echo
command arg: true
这里的最后一个参数应该被Bash解析为一个单独的参数,然而它被分成单个的单词。
我做错了什么?我希望echo true
显示为一个参数。
答案 0 :(得分:2)
除了正在进行单词分割的'echo true'
部分之外,您获得了正确的输出。您需要在代码中使用双引号:
main "$@"
在功能中:
function main() {
local commands=("$@") # need () and double quotes here
for command in "${commands[@]}" ; do
echo "command arg: $command"
done
}
该函数获取自己的$@
副本,因此您不需要制作本地副本。
通过这些更改,我们得到了这个输出:
command arg: /bin/bash
command arg: -c
command arg: echo true
通常,将shell命令存储在变量中并不好。请参阅BashFAQ/050。
另见:
答案 1 :(得分:0)
您可能希望做更多类似的事情:
function main() {
while [ $# -gt 0 ]
do
echo "$1"
shift
done
}
main /bin/bash -c "echo true"
密钥实际为$#
,它计算命令行参数的数量(不包括调用名称$0
)。环境变量$#
自动设置为命令行参数的数量。如果使用以下命令行调用函数/脚本:
$ main /bin/bash -c "echo true"
$#
的价值为" 3"对于参数:" / bin / bash"," -c"和" echo true"。最后一个计为一个参数,因为它们包含在引号内。
shift
命令"移位"所有命令行参数左侧一个位置。 main
)。 答案 2 :(得分:0)
引用@传递给main是你的问题,但我想我会提到你也不需要在main中分配值来使用它。 您可以执行以下操作:
main()
{
for command
do
...
done
}
main "$@"