在以下示例中,我对标记为(!!)
的行感到惊讶:
log1 () { echo $@; }
log2 () { echo "$@"; }
X=(a b)
IFS='|'
echo ${X[@]} # prints a b
echo "${X[@]}" # prints a b
echo ${X[*]} # prints a b
echo "${X[*]}" # prints a|b
echo "---"
log1 ${X[@]} # prints a b
log1 "${X[@]}" # prints a b
log1 ${X[*]} # prints a b
log1 "${X[*]}" # prints a b (!!)
echo "---"
log2 ${X[@]} # prints a b
log2 "${X[@]}" # prints a b
log2 ${X[*]} # prints a b
log2 "${X[*]}" # prints a|b
以下是我的理解:
${X[*]}
和${X[@]}
都扩展为a b
"${X[*]}"
扩展为"a|b"
"${X[@]}"
扩展为"a" "b"
$*
和$@
的行为与${X[*]}
和${X[@]}
相同,只是它们的内容为程序或函数的参数
这似乎得到了Bash手册的确认。
在行log1 "${X[*]}"
中,因此我期望引用的表达式会扩展为"a|b",然后传递给log1函数。该函数有一个字符串参数,它会显示该参数。为什么会发生其他事情呢?
如果您的答案能够得到手册/标准参考支持,那就太酷了!
printf
可能是最简单的选项(例如:https://dev59.com/12cs5IYBdhLWcg3wRB7h)。 - Norswap$@
。(有一些特殊情况下,您可能会故意不引用$*
或其他参数,但$@
存在是为了被引用;它与$*
完全相同。) - chepner