条件语句
跟其它程序设计语言一样,Bash中的条件语句让我们可以决定一个操作是否被执行。结果取决于一个包在[[ ]]
里的表达式。
条件表达式可以包含&&
和||
运算符,分别对应 与 和 或 。除此之外还有很多有用的表达式。
共有两个不同的条件表达式:if
和case
。
基元和组合表达式
由[[ ]]
(sh
中是[ ]
)包起来的表达式被称作 检测命令 或 基元。这些表达式帮助我们检测一个条件的结果。在下面的表里,为了兼容sh
,我们用的是[ ]
。这里可以找到有关bash中单双中括号区别的答案。
跟文件系统相关:
基元 | 含义 |
---|---|
[ -e FILE ] |
如果FILE 存在 (exists),为真 |
[ -f FILE ] |
如果FILE 存在且为一个普通文件(file),为真 |
[ -d FILE ] |
如果FILE 存在且为一个目录(directory),为真 |
[ -s FILE ] |
如果FILE 存在且非空(size 大于0),为真 |
[ -r FILE ] |
如果FILE 存在且有读权限(readable),为真 |
[ -w FILE ] |
如果FILE 存在且有写权限(writable),为真 |
[ -x FILE ] |
如果FILE 存在且有可执行权限(executable),为真 |
[ -L FILE ] |
如果FILE 存在且为一个符号链接(link),为真 |
[ FILE1 -nt FILE2 ] |
FILE1 比FILE2 新(newer than) |
[ FILE1 -ot FILE2 ] |
FILE1 比FILE2 旧(older than) |
跟字符串相关:
基元 | 含义 |
---|---|
[ -z STR ] |
STR 为空(长度为0,zero) |
[ -n STR ] |
STR 非空(长度非0,non-zero) |
[ STR1 == STR2 ] |
STR1 和STR2 相等 |
[ STR1 != STR2 ] |
STR1 和STR2 不等 |
算数二元运算符:
基元 | 含义 |
---|---|
[ ARG1 -eq ARG2 ] |
ARG1 和ARG2 相等(equal) |
[ ARG1 -ne ARG2 ] |
ARG1 和ARG2 不等(not equal) |
[ ARG1 -lt ARG2 ] |
ARG1 小于ARG2 (less than) |
[ ARG1 -le ARG2 ] |
ARG1 小于等于ARG2 (less than or equal) |
[ ARG1 -gt ARG2 ] |
ARG1 大于ARG2 (greater than) |
[ ARG1 -ge ARG2 ] |
ARG1 大于等于ARG2 (greater than or equal) |
条件语句可以跟 组合表达式 配合使用:
Operation | Effect |
---|---|
[ ! EXPR ] |
如果EXPR 为假,为真 |
[ (EXPR) ] |
返回EXPR 的值 |
[ EXPR1 -a EXPR2 ] |
逻辑 与, 如果EXPR1 和(and)EXPR2 都为真,为真 |
[ EXPR1 -o EXPR2 ] |
逻辑 或, 如果EXPR1 或(or)EXPR2 为真,为真 |
当然,还有很多有用的基元,在Bash的man页面能很容易找到它们。
使用if
if
在使用上跟其它语言相同。如果中括号里的表达式为真,那么then
和fi
之间的代码会被执行。fi
标志着条件代码块的结束。
# 写成一行
if [[ 1 -eq 1 ]]; then echo "true"; fi
# 写成多行
if [[ 1 -eq 1 ]]; then
echo "true"
fi
同样,我们可以使用if..else
语句,例如:
# 写成一行
if [[ 2 -ne 1 ]]; then echo "true"; else echo "false"; fi
# 写成多行
if [[ 2 -ne 1 ]]; then
echo "true"
else
echo "false"
fi
有些时候,if..else
不能满足我们的要求。别忘了if..elif..else
,使用起来也很方便。
看下面的例子:
if [[ `uname` == "Adam" ]]; then
echo "Do not eat an apple!"
elif [[ `uname` == "Eva" ]]; then
echo "Do not take an apple!"
else
echo "Apples are delicious!"
fi
使用case
如果你需要面对很多情况,分别要采取不同的措施,那么使用case
会比嵌套的if
更有用。使用case
来解决复杂的条件判断,看起来像下面这样:
case "$extension" in
"jpg"|"jpeg")
echo "It's image with jpeg extension."
;;
"png")
echo "It's image with png extension."
;;
"gif")
echo "Oh, it's a giphy!"
;;
*)
echo "Woops! It's not image!"
;;
esac
每种情况都是匹配了某个模式的表达式。|
用来分割多个模式,)
用来结束一个模式序列。第一个匹配上的模式对应的命令将会被执行。*
代表任何不匹配以上给定模式的模式。命令块儿之间要用;;
分隔。