Bash参考手册表示
[ string ]
和
如果字符串的长度不为0,[-n string ]
将返回 true
但事实并非如此
greet=
if [ $greet ]; then
echo '1'
else
echo '2'
fi
if [ -n $greet ]; then
echo '1'
else
echo '2'
fi
输出为
2
1
Bash参考手册只是说
-n string
string
True if the length of string is non-zero.
那么,这两种形式之间真正的区别是什么?
答案 0 :(得分:4)
正如@ user1502952所说,你需要使用双引号;但是让我解释为什么。假设您执行:
greet=
[ -n $greet ] && echo "it's nonblank"
当shell解析[ -n $greet ]
部分时,它会将$greet
扩展为空字符串,然后进行单词拆分。例如,如果$greet
扩展为中间带空格的东西,它会将每个“单词”视为[
命令的单独参数。但是,在这种情况下,$greet
扩展为空,它根本不包含“单词”,因此被视为[
的零参数 - 它实际上从命令中消失。因此[ -n $greet ]
相当于[ -n ]
,会检查字符串“-n”是否为非空白。它是,所以评估为真。
将此与[ -n "$greet" ]
进行比较:在这种情况下,双引号允许扩展$greet
,但会阻止分词。因此[
命令实际上获得了一个零长度的第二个参数,意识到-n
应该是一个运算符,并获得预期的答案。
答案 1 :(得分:1)
当您使用-n选项时,需要使用双引号。
if [ -n "$greet" ]
当字符串为空时,上面的表达式求值为false,因为长度为零。
if [ "$greet" ]
当字符串为空时,这也会计算为false。
此外,为了检查空字符串,可以使用-z选项。
if [ -z "$greet" ]
这将是真的,因为字符串是空的。
答案 2 :(得分:0)
Bash在[
内执行分词,但不在[[
内执行分词,因此如果您使用[[
,则不必引用参数:
$ x=
$ [ -n $x ]; echo $?; [ -n "$x" ]; echo $?
0
1
$ [[ -n $x ]]; echo $?; [[ -n "$x" ]]; echo $?
1
1
type
将[[ $x ]]
显示为[[ -n $x ]]
:
$ f() { [[ $x ]]; }; type f
f is a function
f ()
{
[[ -n $x ]]
}