Shell 脚本速查表
本页面汇总了 Shell 脚本编程最常用的语法和命令,方便快速查阅。
脚本结构
#!/bin/bash
# Shebang:指定解释器
set -e # 命令失败时退出
set -u # 使用未定义变量时报错
set -x # 打印执行的命令
set -o pipefail # 管道中任何命令失败时返回失败
变量
定义和使用
name="John" # 定义变量(等号两边不能有空格)
echo $name # 使用变量
echo ${name} # 推荐使用花括号
echo "${name}'s home" # 字符串中使用
readonly PI=3.14 # 只读变量
unset name # 删除变量
特殊变量
| 变量 | 含义 |
|---|---|
$0 | 脚本名称 |
$1-$9 | 第 1-9 个参数 |
$# | 参数个数 |
$@ | 所有参数(独立字符串) |
$* | 所有参数(单个字符串) |
$? | 上一个命令的退出状态 |
$$ | 当前进程 PID |
$! | 最后一个后台进程 PID |
$RANDOM | 随机数 0-32767 |
$LINENO | 当前行号 |
参数扩展
${var:-default} # var 未定义则使用 default
${var:=default} # var 未定义则赋值并使用
${var:+alternative} # var 已定义则使用 alternative
${#var} # 字符串长度
${var:start:length} # 子字符串
${var#pattern} # 删除最短前缀匹配
${var##pattern} # 删除最长前缀匹配
${var%pattern} # 删除最短后缀匹配
${var%%pattern} # 删除最长后缀匹配
${var/old/new} # 替换第一个匹配
${var//old/new} # 替换所有匹配
${var^} # 首字母大写
${var^^} # 全部大写
${var,} # 首字母小写
${var,,} # 全部小写
数组
索引数组
arr=(a b c d) # 创建数组
arr[4]=e # 添加元素
arr+=(f g) # 追加元素
echo ${arr[0]} # 访问元素
echo ${arr[@]} # 所有元素
echo ${#arr[@]} # 数组长度
echo ${!arr[@]} # 所有索引
unset arr[1] # 删除元素
unset arr # 删除数组
关联数组
declare -A dict
dict=([name]="John" [age]=25)
echo ${dict[name]} # 访问元素
echo ${!dict[@]} # 所有键
echo ${dict[@]} # 所有值
字符串
str="Hello, World!"
# 长度
${#str} # 13
# 子字符串
${str:0:5} # Hello
${str:7} # World!
# 替换
${str/World/Shell} # Hello, Shell!
# 大小写
${str^^} # HELLO, WORLD!
${str,,} # hello, world!
条件判断
文件测试
| 运算符 | 含义 |
|---|---|
-e | 存在 |
-f | 是普通文件 |
-d | 是目录 |
-r | 可读 |
-w | 可写 |
-x | 可执行 |
-s | 非空 |
-L | 是符号链接 |
数值比较
| 运算符 | 含义 |
|---|---|
-eq | 等于 |
-ne | 不等于 |
-gt | 大于 |
-ge | 大于等于 |
-lt | 小于 |
-le | 小于等于 |
字符串比较
| 运算符 | 含义 |
|---|---|
= | 相等 |
!= | 不相等 |
-z | 长度为 0 |
-n | 长度不为 0 |
条件语法
# if 语句
if [[ condition ]]; then
commands
elif [[ condition ]]; then
commands
else
commands
fi
# [ ] 和 [[ ]]
[ "$a" -eq "$b" ] # 基本测试
[[ $a -eq $b ]] # 扩展测试(推荐)
(( a == b )) # 算术测试
# 逻辑运算
[[ -f "$f" && -r "$f" ]] # 与
[[ -f "$f" || -d "$f" ]] # 或
[[ ! -f "$f" ]] # 非
循环
for 循环
# 遍历列表
for item in a b c; do
echo $item
done
# 遍历范围
for i in {1..5}; do
echo $i
done
# C 风格
for ((i=0; i<5; i++)); do
echo $i
done
# 遍历数组
for item in "${arr[@]}"; do
echo $item
done
while 循环
while [[ condition ]]; do
commands
done
# 读取文件
while IFS= read -r line; do
echo $line
done < file.txt
# 无限循环
while true; do
commands
done
until 循环
until [[ condition ]]; do
commands
done
循环控制
break # 跳出循环
break 2 # 跳出 2 层循环
continue # 跳过当前迭代
case 语句
case $var in
pattern1)
commands
;;
pattern2|pattern3)
commands
;;
*)
default commands
;;
esac
函数
# 定义函数
func() {
local var="local" # 局部变量
echo "Hello, $1!"
return 0 # 返回状态码
}
# 调用
func "World"
# 获取返回值
result=$(func "World") # 捕获输出
输入输出
重定向
cmd > file # 输出到文件(覆盖)
cmd >> file # 输出到文件(追加)
cmd 2> file # 错误输出到文件
cmd &> file # 所有输出到文件
cmd < file # 从文件输入
cmd1 | cmd2 # 管道
Here Document
cat << EOF
Line 1
Line 2
$variable # 会展开
EOF
cat << 'EOF'
$variable # 不会展开
EOF
Here String
grep "pattern" <<< "string"
读取输入
read var # 读取一行
read -p "Prompt: " var # 带提示
read -s var # 静默输入(密码)
read -t 5 var # 5 秒超时
read -a arr # 读取到数组
IFS=',' read -a arr # 指定分隔符
算术运算
# 算术扩展
$((a + b)) # 加
$((a - b)) # 减
$((a * b)) # 乘
$((a / b)) # 除
$((a % b)) # 取模
$((a ** b)) # 幂
# 自增/自减
((i++))
((i--))
# 复合赋值
((i += 5))
# 比较运算符
((a == b)) # 等于
((a != b)) # 不等于
((a > b)) # 大于
((a < b)) # 小于
文本处理
grep
grep "pattern" file # 搜索
grep -i "pattern" file # 忽略大小写
grep -v "pattern" file # 反向匹配
grep -r "pattern" dir # 递归搜索
grep -n "pattern" file # 显示行号
grep -c "pattern" file # 统计匹配数
grep -l "pattern" *.txt # 只显示文件名
grep -E "regex" file # 扩展正则
grep -o "pattern" file # 只显示匹配部分
sed
sed 's/old/new/' file # 替换第一个
sed 's/old/new/g' file # 替换所有
sed -i 's/old/new/g' file # 直接修改文件
sed '3d' file # 删除第 3 行
sed '/pattern/d' file # 删除匹配行
sed -n '5,10p' file # 打印第 5-10 行
awk
awk '{print $1}' file # 打印第 1 列
awk -F: '{print $1}' file # 指定分隔符
awk '$3 > 100' file # 条件过滤
awk '{sum+=$1} END{print sum}' # 求和
awk 'NR==5' file # 打印第 5 行
awk 'END{print NR}' file # 统计行数
cut
cut -d: -f1 file # 按 : 分隔取第 1 列
cut -c1-5 file # 取第 1-5 个字符
sort
sort file # 排序
sort -n file # 数值排序
sort -r file # 逆序
sort -u file # 去重排序
sort -t: -k3 file # 按第 3 列排序
uniq
sort file | uniq # 去重
sort file | uniq -c # 统计出现次数
sort file | uniq -d # 只显示重复行
信号处理
# trap 语法
trap 'commands' signals
# 常用示例
trap 'echo "Interrupted"; exit' INT
trap 'cleanup; exit' EXIT
trap '' INT # 忽略信号
trap - INT # 恢复默认行为
常见信号
| 信号 | 编号 | 含义 |
|---|---|---|
| SIGINT | 2 | Ctrl+C |
| SIGTERM | 15 | 终止请求 |
| SIGKILL | 9 | 强制终止 |
| SIGHUP | 1 | 挂起 |
后台任务
cmd & # 后台运行
nohup cmd & # 退出终端后继续运行
jobs # 查看后台任务
fg %1 # 调到前台
bg %1 # 放到后台
wait # 等待所有后台任务
wait $pid # 等待指定进程
调试
bash -n script.sh # 检查语法
bash -x script.sh # 打印执行的命令
bash -v script.sh # 打印读取的行
# 脚本内
set -x # 开启调试
set +x # 关闭调试
set -e # 遇错退出
set -u # 未定义变量报错
常用命令
文件操作
ls -la # 列出文件
cp source dest # 复制
mv source dest # 移动/重命名
rm file # 删除文件
rm -rf dir # 删除目录
mkdir -p dir # 创建目录
touch file # 创建空文件
ln -s target link # 创建符号链接
文件查看
cat file # 显示内容
less file # 分页查看
head -n 20 file # 前 20 行
tail -n 20 file # 后 20 行
tail -f file # 实时追踪
wc -l file # 统计行数
查找
find . -name "*.txt" # 按名称查找
find . -type f -size +100M # 按大小查找
find . -mtime -7 # 7 天内修改
which cmd # 查找命令位置
whereis cmd # 查找命令相关文件
进程管理
ps aux # 查看进程
top # 动态监控
kill PID # 终止进程
kill -9 PID # 强制终止
killall name # 按名称终止
pgrep name # 查找进程 PID
网络
ping host # 测试连通
curl url # 请求 URL
wget url # 下载文件
ssh user@host # SSH 连接
scp file user@host:path # 复制文件
netstat -tulpn # 查看端口
lsof -i :port # 查看端口占用
快捷键
| 快捷键 | 功能 |
|---|---|
Tab | 自动补全 |
Ctrl+C | 终止命令 |
Ctrl+D | 退出 Shell |
Ctrl+L | 清屏 |
Ctrl+A | 光标移到行首 |
Ctrl+E | 光标移到行尾 |
Ctrl+U | 删除光标前内容 |
Ctrl+K | 删除光标后内容 |
Ctrl+R | 搜索历史 |
Ctrl+Z | 暂停任务 |
通配符
| 符号 | 含义 |
|---|---|
* | 匹配任意字符 |
? | 匹配单个字符 |
[abc] | 匹配 a、b、c |
[a-z] | 匹配范围 |
[!abc] | 不匹配 |
{a,b} | 匹配 a 或 b |
花括号扩展
{a,b,c} # a b c
{1..5} # 1 2 3 4 5
{a..e} # a b c d e
{1..10..2} # 1 3 5 7 9
file{,.bak} # file file.bak