您的位置:首页 > 运维架构 > Shell

SHELL中$@和$*的比较

2015-07-29 00:00 537 查看
[root@localhost ceshi]# cat test.sh
#!/bin/bash
# test.sh
echo "-------------ISF is set to \"-seperator\" ------------"
IFS="-seperator"; # 注意 seperator前有一个减号(-)
for i in "$@"; do echo "@ '$i'"; done
for i in "$*"; do echo "* '$i'"; done

echo "-------------ISF is set to null ------------------------"
IFS=
for i in "$@"; do echo "@ '$i'"; done
for i in "$*"; do echo "* '$i'"; done

echo "-------------ISF is unset ------------------------"
unset IFS
for i in "$@"; do echo "@ '$i'"; done
for i in "$*"; do echo "* '$i'"; done

echo '---------$* and $@ are not put into double quotes(" ")-------'
for i in $@; do echo "@ '$i'"; done
for i in $*; do echo "* '$i'"; done

test.sh aa bb cc执行的结果如下:
[root@localhost ceshi]# sh test.sh aa bb cc
-------------ISF is set to "-seperator" ------------
@ 'aa'
@ 'bb'
@ 'cc'
* 'aa-bb-cc'
-------------ISF is set to null ------------------------
@ 'aa'
@ 'bb'
@ 'cc'
* 'aabbcc'
-------------ISF is unset ------------------------
@ 'aa'
@ 'bb'
@ 'cc'
* 'aa bb cc'
---------$* and $@ are not put into double quotes(" ")-------
@ 'aa'
@ 'bb'
@ 'cc'
* 'aa'
* 'bb'
* 'cc'

由此可见,
1) 当不加双引号("")时, $*,$@被展开时的行为是一样的;
2) 当$*,$@都被放到双引号("")内;
2.1) 如果设置了变量IFS的值并且该值非空, 则$*被展开时使用${IFS}的第一个字符将所有参数(除了参数$0)连接起来, 即"$1c$2c$3c...",其中c表示${IFS}的第一个字符;
2.2) 如果变量IFS为空, 则$*被展开时只是将所有参数(除了参数$0)简单连接起来, 即 “$1$2$3..."
2.3)如果变量IFS没有被定义, 则$*被展开时使用空格字符将所有参数(除了参数$0) 连接起来, 即"$1 $2 $3 ..."
但$@的展开和没有加双引号的情形是一致的。

更多的Shell脚本例子:
#!/bin/bash
set 'apple pie' pears peaches
for i in $* #单引号被去掉,循环单个字符输出#
do echo $i
done

[root@localhost ceshi]# sh test1.sh
apple
pie
pears
peaches
--------------------------------------------------------------

#!/bin/bash
set 'apple pie' pears peaches
for i in "$*" #单引号被去掉,但当作字符串一次输出#
do echo $i
done

[root@localhost ceshi]# sh test2.sh
apple pie pears peaches
-----------------------------------------------------------------

#!/bin/bash
set 'apple pie' pears peaches
for i in $@ #单引号被去掉,循环单个字符输出#
do echo $i
done
[root@localhost ceshi]# sh test3.sh
apple
pie
pears
peaches
-----------------------------------------------------------------

#!/bin/bash
set 'apple pie' pears peaches
for i in "$@" #每个位置参数都将当成一个加引号的字符串:"apple pie","pears ","peaches"#
do echo $i
done
[root@localhost ceshi]# sh test4.sh
apple pie
pears
peaches
-----------------------------------------------------------------

test5.sh

sum=0
for var
in "$@"
do
let sum=sum+$var
done
echo "sum=$sum"

./test1.sh 1 2 3

结果为sum=6
-----------------------------------------------------------------

test6.sh

sum=0
for var
in "$*"
do
let sum=sum+$var
done
echo "sum=$sum"

./test2.sh 1 2 3

结果为sum=1
-----------------------------------------------------------------

分析一:

bash -x test1.sh

结果如下:

+ sum=0
+ for var in ' "$@" '
+ let sum=sum+1
+ for var in ' "$@" '
+ let sum=sum+2
+ for var in ' "$@" '
+ let sum=sum+3
+ echo sum=6
sum=6

可以看出for执行了三次,说明for是以""为边界的,因为每个参数是以""被包围的

分析二:

bash -x test2.sh

结果如下:

+ sum=0
+ for var in '"$*"'
+ let sum=sum+1 2 3
+ echo sum=1
sum=1

可以看出循环只执行了一次,说明$*整体是以""包围的,不是每个参数被""包围,因此只执行一次

一个更直接的例子是:

for var
in "a b c"
do
echo "${var}@"
done

打印:

a b c@

for var
in "a" "b" "c"
do
echo "${var}@"
done

打印:

a@

b@

c@
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  null