1read命令 键盘读取变量的值
[root@meditation ~]# read a b
hello world
[root@meditation ~]# echo $a
hello
[root@meditation ~]# echo $b
world
[root@meditation ~]# read -p "input your passwd:" -s -t 20 passwd
- -p:显示提示信息
- -s:隐藏密码
- -t:设置时间,20秒后关闭
- -n:长度限制.-n 12:最多12个字符
- -r:允许输入特殊字符
也可以通过和echo搭配,实现输入密码效果
[root@meditation ~]# echo -n "input your passwd:";read passw
input your passwd:123456
简单交互输入信息
[root@meditation ~]# cat read.sh
#!/bin/bash
read -p "请输入姓名:" name
read -p "请输入年龄:" age
read -p "请输入性别:" sex
cat<<eof
******************
你的基本信息如下:
姓名: $name
年龄: $age
性别: $sex
******************
eof
[root@meditation ~]# bash ./read.sh
请输入姓名:苍老师
请输入年龄:34
请输入性别:女
******************
你的基本信息如下:
姓名: 苍老师
年龄: 34
性别: 女
******************
[root@meditation ~]#
2流程控制语句if
2.1单分支if语句
[root@meditation ~]# cat if1.sh
#!/bin/bash
if ls /mnt
then
echo "it is ok"
fi
[root@meditation ~]# bash if1.sh
it is ok
2.2双分支if语句
[root@meditation ~]# cat if2.sh
#!/bin/bash
if grep sss /etc/passwd
then
echo "it's ok"
else
echo "it's err"
fi
[root@meditation ~]# bash if2.sh
it's err
2.3多分支if语句
[root@meditation ~]# cat if3.sh
#!/bin/bash
read -p "input a user:" users
if grep $users /etc/passwd
then
echo "the user $users exists on this system"
elif ls -d /home/$users
then
echo "$users has a home direcotry"
echo "the user $users not exists on this system"
else
echo "$users nor has a home direcotry"
echo "the user $users not exists on this system"
fi
[root@meditation ~]# bash if3.sh
input a user:sunlizhao31
sunlizhao31:x:1003:1003::/home/sunlizhao31:/bin/bash
the user sunlizhao31 exists on this system
3test测试命令
- 如果结果是对的,也叫结果为真,用$?=0表示. 反之为假,用非0表示
3.1数值比较
-eq | 等于则为真 | "$a" -eq "$b" |
-ne | 不等于则为真 | "$a" -ne "$b" |
-gt | 大于则为真 | "$a" -gt "$b" |
-ge | 大于等于则为真 | "$a" -ge "$b" |
-lt | 小于则为真 | "$a" -lt "$b" |
-le | 小于等于则为真 | "$a" -le "$b" |
两种写法:test和[]
[root@meditation ~]# cat test1.sh
#!/bin/bash
if test 2 -eq 1
then
echo "ok"
else
echo "err"
fi
[root@meditation ~]# bash test1.sh
err
[root@meditation ~]# cat test2.sh
#!/bin/bash
if [ 2 -le 10 ]
then
echo "ok"
else
echo "err"
fi
[root@meditation ~]# bash test2.sh
ok
用户输入两个数字,判断大小
[root@meditation ~]# cat test3.sh
#!/bin/bash
read -p "input var1: " var1
read -p "input var2: " var2
if [ $var1 -gt $var2 ]
then
echo "$var1 > $var2"
elif [ $var1 -lt $var2 ]
then
echo "$var1 < $var2"
else
echo "$var1 = $var2"
fi
[root@meditation ~]# bash test3.sh
input var1: 12
input var2: 21
12 < 21
[root@meditation ~]# bash test3.sh
input var1: 12
input var2: 12
12 = 12
3.2字符串比较
== | 等于为真 |
!= | 不相等为真 |
-z 字符串 | 字符串的长度为0则为真 |
-n 字符串 | 字符串的长度不为空则为真 |
str1>str2 | str1大于str2为真 |
str1<str2 | str1小于str2为真 |
在做字符串比较时
- 大于号和小于号必须转义,要不然shell会把它当做重定向符号
- 大于和小于他们的顺序和sort排序是不一样的test测试中,使用的是ascii顺序,大写字母小于小写字母
3.3文件比较
-e 文件名 | 如果文件或目录存在则为真 |
-r 文件名 | 如果文件存在且可读则为真 |
-w 文件名 | 如果文件存在且可写则为真 |
-x 文件名 | 如果文件存在且可执行则为真 |
-s 文件名 | 如果文件存在且至少有一个字符则为真 |
-d 文件名 | 如果文件存在且为目录则为真 |
-f 文件名 | 如果文件存在且为普通文件则为真 |
-c 文件名 | 如果文件存在且为字符型文件则为真 |
-b 文件名 | 如果文件存在且为块特殊文件则为真 |
file1 -nt file2 | 检查file1是否比file2新 |
file1 -ot file2 | 检查file1是否比file2新 |
[root@localhost test]# cat test.sh
#!/bin/bash
if [ -e /etc/passwd ]
then
echo ok
else
echo err
fi
[root@localhost test]# bash test.sh
ok
[root@localhost test]# test -e /etc/passwd && echo ok || echo err
ok
4流程控制过程中复杂条件和通配符
4.1复杂条件
两个条件都为真, 或有一个为真就执行
判断第一种
if [条件判断一] &&(||) [条件判断二];then
命令一
elif [条件判断三] &&(||) [条件判断四];then
命令二
else
其他命令
fi
判断第二种
if [[ 条件判断一 &&(||) 条件判断二 ]];then
命令一
elif [[ 条件判断三 &&(||) 条件判断四 ]];then
命令二
else
其他命令
fi
[]和[[]]的区别
[[]]是[]运算符的扩充;能够支持*,<,>等符号,不需要转义
[root@localhost ~]# if [[ $USER == r* ]] ; then echo "hello,$USER" ; else echo $USER not; fi
hello,root
[root@localhost ~]# if [ $USER == r* ] ; then echo "hello,$USER" ; else echo $USER not; fi
root not
- 所有的字符与逻辑运算符需要用"空格"分开,不能连在一起
- 在[]表达式中,常见的>,<需要加转义符,进行大小比较
- 进行逻辑运算符&&,||比较时,如果用的[]符号,则用在外面,如[] && [] || []
如果在[]里进行逻辑与或的比较,则用-a,-o进行表示,如[[x -a y -o z]] [[]]是[]运算符的扩充;能够支持*,<,>等符号,不需要转义,里面支持逻辑运算符||,&& 不再使用-a,-o
- [[]]能进行算术扩展,而[]不行.
[[]]可以用于高级字符串处理,比如模糊匹配
4.2通配符
* | 匹配0个或者多个字符 a*b,a语b之间可以有任意长度的任意字符,也可以一个都没有,如ab,axybdb |
? | 匹配任意一个字符. a?b,a与b之间必须也只能是一个字符,可以是任意字符如axb,abb |
[list] | 匹配list中任意单一字符,a[xyz]b,a与b之间只能匹配一个字符,但是只能是x,y或者z 如axb |
[!list] | 匹配处了list中的任意单一字符. a[!0-9] ab之间必须也只能有一个字符,但不能是阿拉伯数字.匹配如 axb |
[a-z] | 匹配a到z中的任意单一字符.[string1,string2,...]匹配string1或者string2或者更多中的一个字符串 |
[root@meditation ~]# ls /etc/*.conf
/etc/asound.conf /etc/libaudit.conf /etc/pam_url.conf /etc/tcsd.conf
...
[root@meditation ~]# ls /etc/???.conf
/etc/ntp.conf /etc/sos.conf /etc/yum.conf
[root@meditation ~]# touch /opt/a{1,2,3}.txt
[root@meditation ~]# ls /opt/a[123].txt
/opt/a1.txt /opt/a2.txt /opt/a3.txt
[root@meditation ~]# ls /opt/a[1,2,3].txt
/opt/a1.txt /opt/a2.txt /opt/a3.txt
5实战:三个shell脚本实战
5.1检查服务是否在运行
[root@meditation ~]# cat status3.sh
#!/bin/bash
if [ $# -ge 1 ] ; then
systemctl status $1 > /dev/null
if [ $? -eq 0 ] ; then
echo "服务正在运行"
else
systemctl start $1
echo "正在打开"
fi
else
echo "格式错误"
fi
[root@meditation ~]# chmod +x status3.sh
[root@meditation ~]# ./status3.sh httpd
服务正在运行
5.2根据成绩判读等级
[root@meditation ~]# cat cjcx.sh
#!/bin/bash
read -p "请您输入成绩: " cj
if [ $cj -ge 0 ] && [ $cj -lt 60 ] ; then
echo "补考!"
elif [ $cj -ge 60 ] && [ $cj -lt 80 ] ; then
echo "良好"
elif [ $cj -ge 80 ] && [ $cj -lt 90 ] ; then
echo "优秀"
elif [ $cj -ge 90 ] && [ $cj -le 100 ] ; then
echo "你太棒了"
else
echo "请输入0-100之内的有效成绩"
fi
[root@meditation ~]# bash cjcx.sh
请您输入成绩: 1
补考!
[root@meditation ~]# bash cjcx.sh
请您输入成绩: 70
良好
[root@meditation ~]# bash cjcx.sh
请您输入成绩: 100
你太棒了
5.3自动备份某个目录
[root@meditation ~]# cat etcbak.sh
#!/bin/bash
baknamefile=`date +%F`
bakdir=/etcbak
srcdir=/etc
[ -e $bakdir ] || mkdir $bakdir
tar -zcvf ${bakdir}/${baknamefile}-etc.tar.gz $srcdir
echo "==================="
ls -lh ${bakdir}/${baknamefile}-etc.tar.gz
[root@meditation ~]# bash etcbak.sh
...
/etc/cloud/templates/resolv.conf.tmpl
/etc/sysctl.conf
/etc/gshadow-
===================
-rw-r--r-- 1 root root 9.5M Aug 4 20:43 /etcbak/2019-08-04-etc.tar.gz