shell脚本
本质 shell命令的 有序集合
一种解释型 语言 不需要编译
方便操作者 对重复性的劳动进行 编程
一种无类型语言 变量没有类型 或 字符串类型
注意事项: 对标点符号 和 格式 非常严格 特别是空格
创建一个shell脚本步骤
1. 创建一个普通文件 通常 后缀.sh
touch 文件名.sh
2. 修改权限 添加可执行权限
chmod 777 文件名sh3. 写脚本
vim 文件名.sh第一行 (一般默认写) #!/bin/bash
4. 运行脚本 ./文件名.sh
如下,是一个shell脚本代码,他的用途是每次运行这个shell文件时会生成新的脚本文件
#!/bin/bash
hell脚本 创建shell脚本
# 定义一个变量
#NAME=3.sh
#位置变量
NAME=$1
# 引用变量 $变量名
echo 用户$USER正在创建$NAME文件
touch $NAME
echo 正在修改文件权限
chmod 777 $NAME
echo 正在写入开始行
echo "#!/bin/bash" > $NAME
echo 脚本$NAME创建完成
#vim $NAME
运行
shell 中的变量
变量: 多用于 代指文件名 各种名字 或参数 命令等
用户自定义变量:
变量定义 变量名=值 等号两边 没有空格
变量使用 引用其值 $变量名 本质是字符替换位置变量:
$0 运行脚本的指令本身
$1,$2,……$9 分别包含第一个到第九个命令行参数预定义变量: 有终端预先定义的一些变量
由系统保留和维护的一组特殊的变量,这些变量通常用于保存程序运行状态等
$# 包含命令行参数的个数
$@ 包含所有命令行参数:“$1,$2,……$9”
$? 包含前一个命令的退出状态
$* 包含所有命令行参数:“$1,$2,……$9”
$$ 包含正在执行进程的ID号环境变量:
一组存储终端环境参数的 变量
export 命令 可以打印输出 终端所有的环境变量
PWD 存储当前工作路径
USER 存储当前终端的登录用户
HOME 存储当前用户的家目录
PATH 存储当前终端 的命令搜索路径echo $PATH
/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games:/opt/gcc-4.6.4/bin:/home/xwq/esp8266/xtensa-lx106-elf/bin:/home/xwq/.local/binshell脚本的 输入输出:
echo 输出字符串
read 从终端读取字符串shell中 的算数运算
expr 数学表达式 每个符号与数值 间都要有空格分开
支持 + - \* / % 但只能做 整数运算 不能做小数运算
#!/bin/bash
echo "请输出两个数的和:"
read a b
#读取输入的两个数赋值给a b
echo "a=$a b=$b"
#
#使用命令置换将命令的输出作为变量的参数
c=`expr $a + $b`
echo $a+$b=$c
echo $a+$b=`expr $a + $b`
shell 表达式
字符串测试
s1 == s2 测试两个字符串的内容是否完全一样
s1 != s2 测试两个字符串的内容是否有差异
-z s1 测试s1 字符串的长度是否为0
-n s1 测试s1 字符串的长度是否不为0
整数测试
a -eq b 测试a 与b 是否相等
a -ne b 测试a 与b 是否不相等
a -gt b 测试a 是否大于b
a -ge b 测试a 是否大于等于b
a -lt b 测试a 是否小于b
a -le b 测试a 是否小于等于b
-d name 测试name 是否为一个目录
-e name 测试一个文件是否存在
-f name 测试name 是否为普通文件
-L name 测试name 是否为符号链接
-r name 测试name 文件是否存在且为可读
-w name 测试name 文件是否存在且为可写
-x name 测试name 文件是否存在且为可执行
-s name 测试name 文件是否存在且其长度不为0
f1 -nt f2 测试文件f1 是否比文件f2 更新
f1 -ot f2 测试文件f1 是否比文件f2 更旧
例如:输入一个文件名 判断该文件 是否存在, 若存在 判断是否为 普通文件且是空的
则 删除它
#!/bin/bash
echo "输入一个文件名:"
read a
echo "$a"
if [ -e $a ]
then
echo "有这个文件"
if [ -f $a ]
then
echo "是普通文件"
if [ -s $a ]
then
echo "文件存在且长度不为零"
else
echo "删除的文件是$a"
rm $a
fi
fi
fi
程序结构
if 结构
if [ 表达式 ]
then
命令块1
else
命令块2
fi没有else 可以省略
if [ 表达式 ]
then
命令块1
ficase 多分支结构
结构:
case $变量名 in
值1) 命令块1
;;
值2) 命令块2
;;
...
*) 命令块n
esac运行逻辑 将变量中字符串 与 ) 左边的字符串比较 相等 就 执行后面的命令块
若 不相等 继续向后比较
值可以使用通配符练习: 输入成绩 输出 优良中差
echo "请输入成绩" read cj case $cj in 100) echo "成绩优秀" ;; 9?) echo "成绩优秀" ;; 8?) echo "成绩良好" ;; [67]?) echo "成绩中" ;; *) echo "成绩不及格" ;; esac
循环结构:
for循环 结构1:for (( I=0;I<10;I++ ))
do
循环命令块
done示例: 创建10个文件 文件名为 file_数.txt
结构2:
for 变量名 in 取值列表
do
循环命令块
done取值列表: 以空格 回车 等分隔开的的字符串
每次循环 变量的值 就是 取值列表 中的一个
顺序的示例: 打印输出 当前目录中 所有.sh 文件的内容都打印出来
练习: 写一个脚本实现 将当前目录中 所有的 空的 普通文件 删除
while循环:
while [ 条件表达式 ]
do
循环语句块
done与C的运行逻辑完全一样
循环控制语句 与C的break与continue关键字效果完全一样
break
continuebreak 2
continue 2了解: shell 的函数
函数定义:
函数名()
{
命令块
}函数调用
函数名参数传递 使用位置变量