跳到主要内容

Shell 运算符

Linux Shell 支持多种运算符,这里我们以 Bash 为例,介绍算术运算符、关系运算符、布尔运算符、字符串运算符和文件测试运算符的用法。

算术运算符

运算符说明举例
+加法$(($a + $b))$((a + b))`expr $a + $b`
-减法$(($a - $b))$((a - b))`expr $a - $b`
*乘法$(($a * $b))$((a * b))`expr $a * $b`
/除法$(($a / $b))$((a / b))`expr $a / $b`
%取余$(($a % $b))$((a % b))`expr $a % $b`
=赋值a=$b 将把变量 b 的值赋给 a。

说明:双小括号表示其中进行数字类型的计算(而且只支持整型),双小括号中还支持布尔值判定,并且当被双小括号框中,整体就应该被看成一个变量。另外,双小括号中支持 C 语言语法规则,可以不加美元符,可以再加单小括号把一些运算先括起来等。

# 默认 a 是字符串类型
a=1;

# 把 a 看成数字,改变前面定义的变量时,必须要加双小括号,
# 或者用 let 语句,否则会把其视为字符串类型
((a++));
let "a++";

# 输出,双小括号应该被看成一个变量
echo $((a+1));

expr 是一款表达式计算工具,使用它能在 shell 中完成表达式的求值操作。但需要注意,expr 表达式要使用反引号包裹,并且表达式和运算符之间要有空格。

关系运算符

关系运算符只支持数字,不支持字符串,除非字符串的值是数字。

运算符说明举例
-eq检测两个数是否相等,相等返回 true。[ $a -eq $b ]
-ne检测两个数是否相等,不相等返回 true。[ $a -ne $b ]
-gt检测左边的数是否大于右边的,如果是,则返回 true。[ $a -gt $b ]
-lt检测左边的数是否小于右边的,如果是,则返回 true。[ $a -lt $b ]
-ge检测左边的数是否大于等于右边的,如果是,则返回 true。[ $a -ge $b ]
-le检测左边的数是否小于等于右边的,如果是,则返回 true。[ $a -le $b ]
==用于比较两个数字,相同则返回 true。[ a == b ]
!=用于比较两个数字,不相同则返回 true。[ a != b ]

注意:条件表达式要放在方括号之间,并且要有空格

布尔运算符

运算符说明举例
!非运算,表达式为 true 则返回 false,否则返回 true。[ !false ]
-o或运算,有一个表达式为 true 则返回 true。[ $a -lt 20 -o $b -gt 100 ]
||或运算,与 -o 相似。`[ $a -lt 20 ]
-a与运算,两个表达式都为 true 才返回 true。[ $a -lt 20 -a $b -gt 100 ]
&&与运算,与 -a 相似。[ $a -lt 20 ] && [ $b -gt 100 ]

字符串运算符

运算符说明举例
-z如果字符串长度为零,则返回 true[ -z $myStr ]
-n如果字符串长度非零,则返回 true[ -n $myStr ]
==如果两个字符串相同,则返回 true[ $myStr = "getiot" ]
!=如果两个字符串不同,则返回 true[ $myStr != "getiot" ]

文件测试运算符

文件测试运算符用于检测 Linux 文件的各种属性,在对文件进行操作之前先检查文件属性,是个好的编程习惯。

运算符说明举例
-b检测文件是否是块设备文件,如果是,则返回 true。[ -b $file ]
-c检测文件是否是字符设备文件,如果是,则返回 true。[ -c $file ]
-d检测文件是否是目录,如果是,则返回 true。[ -d $file ]
-f检测文件是否是普通文件(既不是目录,也不是设备文件),如果是,则返回 true。[ -f $file ]
-p检测文件是否是有名管道,如果是,则返回 true。[ -p $file ]
-r检测文件是否可读,如果是,则返回 true。[ -r $file ]
-w检测文件是否可写,如果是,则返回 true。[ -w $file ]
-x检测文件是否可执行,如果是,则返回 true。[ -x $file ]
-s检测文件是否为空(文件大小是否大于0),不为空返回 true。[ -s $file ]
-e检测文件(包括目录)是否存在,如果是,则返回 true。[ -e $file ]
-S检测文件是否为 socket,如果是,则返回 true。[ -S $file ]
-L检测文件是否存在并且是一个符号链接,如果是,则返回 true。[ -L $file ]

特别注意

== 和 = 的区别

有时候,原来运行得好好的 shell 程序,换个平台就运行不了,例如下面 shell 程序。

#!/bin/sh

if [ $1 == "hello" ]; then
echo "Well done!"
fi

在 Ubuntu 上运行,会出现如下的错误:

[: ==: unexpected operator

这是因为 shell 脚本开头使用 #!/bin/sh,而不是 #!/bin/bash。而 /bin/sh 使用的是 dash,dash 中默认的判断语句是 =,而不是 bash 使用的 ==

$ ls -l /bin/sh
lrwxrwxrwx 1 root root 4 528 20:16 /bin/sh -> dash

解决方法是直接使用 = 符号进行判断,但这样做可能会导致该脚本在其他平台无法正常运行(例如不支持 dash 的嵌入式平台)。为了更好地兼容,可以在 shell 脚本开头使用 #!/bin/bash,或者使用下面命令将系统默认的 shell 链接由 dash 改为 bash。

sudo dpkg-reconfigure dash

选择“否”即可。