bash 中脚本语句的求值顺序是什么?

bash 中脚本语句的求值顺序是什么?

从左到右?或相反亦然?

例子:

If [! -z "$ foo"] && [$ foo2 -eq 0]; then
    echo "something"
fi

首先进行什么评估?

[! -z "$ foo"]

或者

[$ foo2 -eq 0]

谢谢!

答案1

在 shell 脚本中说

if [ ! -z "$foo" ] && [ "$foo2" -eq 0 ]; then
    echo 'something'
fi

第一个测试[ ! -z "$foo" ](最好写成[ -n "$foo" ])将首先运行。第二次测试将仅有的如果第一个测试成功则运行。如果两个都测试成功,意思$foo是一个值不为空并且$foo2算术值等于0,那么echo将被执行。

&&运算符的工作方式与其他语言中的类似运算符类似。外壳实现短路评估&&如果左侧是,则只会评估右侧真的

这个特定的if语句也可以在不使用关键字的情况下编写if,如

[ ! -z "$foo" ] && [ "$foo2" -eq 0 ] && echo 'something'

尽管使用if ...; then ...; fi恕我直言更清楚。

同样,echo只有在以下情况下才会执行两个都前面的测试成功了。

答案2

太长了;博士

如中所述你已有的答案,根据定义与列表在 shell 命令语言中,[ ! -z "$foo" ]首先执行,然后仅当它返回退出状态为零时才[ "$foo2" -eq 0 ]执行。


Bash 中命令的执行顺序在“Shell 命令”部分中指定Bash 参考手册。在下文中,我假设此处提供的定义可能会逐字复制(即使为了方便起见,未将其格式化为引用)。

对于 Bash 和其他 POSIX 兼容的 shell,更正式(但可能不太友好)的定义可以在“Shell 命令语言”一章(特别是“Shell 命令”和“Shell 语法”段落)中找到。The Open Group 基本规格

在代码中

if [ ! -z "$foo" ] && [ "$foo2" -eq 0 ]; then
    echo "something"
fi

我们有一个if 复合命令, 一个并列表和三个简单的命令

条件构造的一般语法if

if test-commands; then
    consequent-commands;
[elif more-test-commands; then
    more-consequents;]
[else alternate-consequents;]
fi

如果 的退出状态test-commands为零,则consequent-commands执行该子句。

我们的test-commands子句是一个 AND 列表,它是一个序列管道用 分隔&&,如

command1 && command2

当且仅当 的退出状态为零command2时才执行where 。command1

AND 列表以左关联性执行。因此:

command1 && command2 && command3

执行起来就好像它被写成一样(使用括号作为伪代码分组运算符并暂时忘记它们在 Bash 语言中的含义):

(((command1) && command2) && command3)

在我们的 AND 列表中

[ ! -z "$foo" ] && [ "$foo2" -eq 0 ]

第一条管道

[ ! -z "$foo" ]

首先执行。仅当第二条管道成功时

[ "$foo2" -eq 0 ]

被执行。列表中最后执行的命令的退出状态是 所考虑的状态if

管道是由一个控制运算符|或分隔的一个或多个命令的序列|&。我们的两个管道都只是简单的命令。

简单命令是由 分隔的单词序列blanks,由 shell 的一个控制运算符终止。简单的命令不会造成执行顺序问题。

根据记录,AND 列表中的简单命令由(内置)命令[及其四个参数组成,分别为!, -z, "$foo",]"$foo2", -eq, 0, ]

最后,consequent-commands我们的复合命令的子句if是简单命令echo "something"——同样,它不会造成任何执行顺序问题。

相关内容