在 Shell 脚本中,条件判断是控制程序流程的基础:根据某个条件的真伪,决定接下来执行哪一部分代码。日常运维中,我们经常需要判断文件是否存在、字符串是否匹配、数值大小关系等,这些都可以通过 test 命令或其等效的方括号 [ ] 来实现。Bash 还提供了更强大的双中括号 [[ ]] 扩展,推荐在脚本中优先使用。
1. 基本语法
条件判断通常配合 if 语句使用,结构如下:
if [ 条件 ]; then
# 条件为真时执行的命令
else
# 条件为假时执行的命令
fi
if 和 fi 是配对的定界符,then 可以写在下一行(此时可省略分号):
if [ 条件 ]
then
命令
fi
如果只需要判断单个条件,也可以用 && 和 || 连接:
[ 条件 ] && echo "真" || echo "假"
2. 常用的条件测试
条件测试可以分为三类:文件测试、字符串比较和整数比较。
文件测试
-e 文件名:文件存在即为真-f 文件名:是普通文件为真-d 文件名:是目录为真-r 文件名:文件可读为真-w 文件名:文件可写为真-x 文件名:文件可执行为真-s 文件名:文件存在且大小大于 0 为真
示例:检查备份目录是否存在,若不存在则创建
backup_dir="/var/backups/myapp"
if [ ! -d "$backup_dir" ]; then
mkdir -p "$backup_dir"
echo "已创建备份目录:$backup_dir"
fi
字符串比较
-z 字符串:字符串长度为 0 为真(空串)-n 字符串:字符串长度不为 0 为真(非空)字符串1 = 字符串2:两者相等为真字符串1 != 字符串2:两者不等为真
注意:使用 [ ] 时,变量和比较符两边必须留空格;变量最好用双引号括起来,避免空值导致语法错误。
user_input="$1"
if [ -z "$user_input" ]; then
echo "错误:需要提供参数"
exit 1
fi
if [ "$user_input" = "admin" ]; then
echo "欢迎,管理员"
else
echo "普通用户:$user_input"
fi
整数比较
数值1 -eq 数值2:等于-ne:不等于-lt:小于-le:小于或等于-gt:大于-ge:大于或等于
示例:判断当前系统的平均负载是否过高
load=$(awk '{print $1}' /proc/loadavg)
threshold=2.0
# 这里需要浮点数比较,用 bc 辅助
if [ "$(echo "$load > $threshold" | bc)" -eq 1 ]; then
echo "警告:系统负载过高($load)"
fi
3. 双中括号 [[ ]] 的增强功能
Bash 的 [[ ]] 是 [ ] 的升级版,更安全、功能更强,且支持 &&(逻辑与)和 ||(逻辑或)直接组合条件,不再需要使用 -a 或 -o。
filename="/etc/passwd"
if [[ -f $filename && -r $filename ]]; then
echo "$filename 是一个可读的普通文件"
fi
字符串比较在 [[ ]] 中可以使用 == 进行模式匹配(通配符),而无需引用变量时担心分词:
response="yes"
if [[ $response == y* ]]; then # 匹配以 y 开头的任何字符串
echo "你同意了"
fi
正则表达式匹配也可以使用 =~ 操作符:
ip="192.168.1.100"
if [[ $ip =~ ^[0-9]+\.[0-9]+\.[0-9]+\.[0-9]+$ ]]; then
echo "合法的 IP 地址格式"
fi
4. 多条件判断:elif 和 case
当有多个互斥条件时,使用 elif 可以避免多层嵌套:
score=85
if [ $score -ge 90 ]; then
echo "优秀"
elif [ $score -ge 80 ]; then
echo "良好"
elif [ $score -ge 60 ]; then
echo "及格"
else
echo "不及格"
fi
对于多分支的字符串匹配,case 语句更加简洁清晰,尤其适合处理脚本参数:
case "$1" in
start)
echo "启动服务..."
;;
stop)
echo "停止服务..."
;;
restart|reload)
echo "重启服务..."
;;
*)
echo "用法:$0 {start|stop|restart}"
exit 1
;;
esac
5. 实用建议
- 始终用双引号包裹变量,避免空值或含空格的值导致语法错误:
[ "$var" = "value" ] - 在脚本中使用
[[ ]]代替[ ],因为它更安全且功能更丰富(但需确认脚本环境为 Bash,而非纯 POSIX sh) - 复杂的逻辑判断可以拆分为多步,用有意义的变量记住中间结果,提高可读性
- 在判断数值大小时,若涉及浮点数,
[ ]和[[ ]]都无法直接处理,需要借助bc或awk
条件判断是 Shell 编程的基石,灵活运用这些简单的测试就能编写出稳健、智能的自动化脚本,处理日常工作中的各类批量任务。