根据这一页、 $@ 和 $* 做几乎相同的事情:
The $@ holds list of all arguments passed to the script.
The $* holds list of all arguments passed to the script.
在搜索完谷歌中的所有热门搜索后,我无法找到任何解释为什么会有两个看似重复的语法。
它们在我的脚本中似乎发挥着相同的作用。
cat foo.sh
#!/bin/bash
echo The parameters passed in are $@
echo The parameters passed in are $*
./foo.sh herp derp
The parameters passed in are herp derp
The parameters passed in are herp derp
- 其中一个比另一个更受青睐吗?
- 为什么有 2 个内置变量可以做完全相同的事情?
其他来源
bash.cyberciti.biz
答案1
他们不一样。 $*
是单个字符串,而$@
是实际数组。要查看差异,请像这样执行以下脚本:
> ./test.sh one two "three four"
剧本:
#!/bin/bash
echo "Using \"\$*\":"
for a in "$*"; do
echo $a;
done
echo -e "\nUsing \$*:"
for a in $*; do
echo $a;
done
echo -e "\nUsing \"\$@\":"
for a in "$@"; do
echo $a;
done
echo -e "\nUsing \$@:"
for a in $@; do
echo $a;
done
四种情况的解释和结果如下。
第一种情况,参数被视为一个long引细绳:
Using "$*":
one two three four
情况 2(不带引号)- 字符串被循环分解为单词for
:
Using $*:
one
two
three
four
情况 3 - 它将 $@ 的每个元素视为带引号的字符串:
Using "$@":
one
two
three four
最后一种情况 - 它将每个元素视为不带引号的字符串,因此最后一个元素再次被分割为for three four
:
Using $@:
one
two
three
four
答案2
区别在于它们的扩展方式。
$*
扩展为单个参数,所有元素均以空格分隔(实际上是 的第一个字符$IFS
)。
$@
扩展到多个参数。
例如
#!/bin/bash
echo "With *:"
for arg in "$*"; do echo "<$arg>"; done
echo
echo "With @:"
for arg in "$@"; do echo "<$arg>"; done
$ /tmp/test.sh 1 2 "3 4"
With *:
<1 2 3 4>
With @:
<1>
<2>
<3 4>
答案3
您可以查看Bash 初学者指南了解更多信息。它们的作用几乎相同,只是分离方式有所不同:
$*
- 扩展到位置参数,从 1 开始。当扩展发生在双引号内时,它会扩展为单个单词,每个参数的值由 IFS 特殊变量的第一个字符分隔。
$@
- 扩展到位置参数,从 1 开始。当扩展发生在双引号内时,每个参数都会扩展为一个单独的单词。
但除非您设置IFS
为默认值以外的值,否则它可能看起来相同。
答案4
其中一个比另一个更受青睐吗?
一个简短的答案是"$@"
。
如果您使用它们时不带双引号,则它们是相同的。在这种情况下,没有谁比另一方更受青睐。但我建议您始终使用双引号,除非您知道自己到底想要什么。
为什么有 2 个内置变量可以做完全相同的事情?
$*
和之间没有区别$@
,但是"$@"
和"$*"
has 之间没有区别。
你可以看到我的回答这个帖子看看它们有何不同。