Shell 中的判断语句:test、[] 与 [[]] 的全面用法
在 Shell 脚本中,判断语句是实现条件逻辑的基础。无论是文件类型检查、权限验证,还是数值 / 字符串比较,都需要通过判断语句实现。本文详细讲解 test 命令、[ ] 和 [[ ]] 三种判断方式的用法及差异。
判断语句的三种形式
Shell 中常用的判断形式有三种,功能类似但语法略有差异:
| 形式 | 说明 | 兼容性 |
|---|---|---|
test 条件 |
基础判断命令 | 所有 Shell 兼容 |
[ 条件 ] |
test 命令的简化写法(注意空格) |
所有 Shell 兼容 |
[[ 条件 ]] |
Bash 扩展语法,支持更多特性 | 仅 Bash、Zsh 等现代 Shell 支持 |
基本用法示例
三种形式可以互换,结果完全一致:
1 | # 判断文件是否为目录 |
输出均为:是目录
文件类型判断
用于检查文件是否存在及类型(目录、普通文件等),常用选项如下:
| 选项 | 含义 | 示例 |
|---|---|---|
-e 文件 |
文件或目录是否存在 | [ -e /etc/passwd ] → 检查密码文件是否存在 |
-d 目录 |
是否为目录且存在 | [ -d /tmp ] → 检查 /tmp 是否为目录 |
-f 文件 |
是否为普通文件且存在 | [ -f ~/.bashrc ] → 检查用户配置文件是否为普通文件 |
-s 文件 |
文件是否存在且非空(大小 > 0) | [ -s log.txt ] → 检查日志文件是否有内容 |
-L 链接 |
是否为符号链接 | [ -L /usr/bin/python ] → 检查 Python 命令是否为软链接 |
-b 设备 |
是否为块设备(如硬盘) | [ -b /dev/sda ] → 检查第一块硬盘 |
-c 设备 |
是否为字符设备(如键盘) | [ -c /dev/tty0 ] → 检查终端设备 |
示例:检查文件状态并输出信息
1 | file="data.txt" |
文件权限判断
检查文件是否拥有读、写、执行权限:
| 选项 | 含义 | 示例 |
|---|---|---|
-r 文件 |
是否有读权限 | [ -r /etc/shadow ] → 普通用户通常返回 false |
-w 文件 |
是否有写权限 | [ -w ~/test.txt ] → 检查用户目录下文件是否可写 |
-x 文件 |
是否有执行权限 | [ -x /usr/bin/ls ] → 检查 ls 命令是否可执行 |
示例:检查脚本是否可执行,若不可执行则添加权限
1 | script="deploy.sh" |
数值比较
用于整数之间的比较(不支持浮点数):
| 选项 | 含义 | 示例 |
|---|---|---|
-eq |
等于(equal) | [ 10 -eq 10 ] → true |
-ne |
不等于(not equal) | [ 10 -ne 20 ] → true |
-gt |
大于(greater than) | [ 20 -gt 10 ] → true |
-lt |
小于(less than) | [ 5 -lt 10 ] → true |
-ge |
大于等于(greater or equal) | [ 10 -ge 10 ] → true |
-le |
小于等于(less or equal) | [ 5 -le 10 ] → true |
示例:比较两个数字大小
1 | a=15 |
字符串比较
用于字符串的 equality、空值等判断:
| 选项 | 含义 | 示例 |
|---|---|---|
= 或 == |
字符串相等(== 仅 [[ ]] 推荐) |
[ "abc" = "abc" ] → true |
!= |
字符串不等 | [ "abc" != "def" ] → true |
-z 字符串 |
字符串长度为 0(空字符串) | [ -z "" ] → true |
-n 字符串 |
字符串长度不为 0(非空) | [ -n "hello" ] → true |
示例:检查用户输入是否为空
1 | read -p "请输入姓名:" name |
逻辑组合判断
多个条件的与、或、非组合:
| 逻辑 | test/[ ] 写法 |
[[ ]] 写法 |
说明 | ||
|---|---|---|---|---|---|
| 与 | 条件1 -a 条件2 |
条件1 && 条件2 |
两个条件都为真才成立 | ||
| 或 | 条件1 -o 条件2 |
` 条件 1 | 条件 2` | 至少一个条件为真 | |
| 非 | ! 条件 |
! 条件 |
条件为假时成立 |
示例:多条件组合判断
1 | # 使用 [ ] 组合条件(-a 表示与) |
[[ ]] 的高级特性
[[ ]] 是 Bash 扩展语法,支持更多便捷功能:
字符串包含判断
无需借助 grep,直接用通配符 * 匹配:
1 | str="hello world" |
正则表达式匹配
使用 =~ 支持正则匹配:
1 | email="test@example.com" |
无需转义特殊字符
[[ ]] 中特殊字符(如 *、?)无需转义,直接使用:
1 | # 判断文件名是否以 .sh 结尾 |
常见错误与注意事项
- 空格问题:
[ 条件 ]和[[ 条件 ]]中,[/[[后、]/]]前必须有空格,如[ -f file ]正确,[-f file]错误。
- 变量引用:
- 字符串变量和可能为空的变量必须用双引号包裹,避免语法错误:
[ "$name" = "root" ]正确,[ $name = "root" ]可能报错(若name为空)。
- 字符串变量和可能为空的变量必须用双引号包裹,避免语法错误:
- 兼容性:
[[ ]]是 Bash 扩展,若脚本需在sh等兼容 Shell 中运行,应使用[ ]。
- 数值与字符串混淆:
- 数值比较用
-eq/-gt等,字符串比较用=/!=,不可混用。
- 数值比较用
v1.3.10