目录
一、介绍
1. Linux提供的Shell解析器
2. bash和sh关系
3. Centos默认的Shell解析器是bash
二、定义
1. 变量名的定义规则
2. 等号周围没有空格
3. 查看变量
4. 删除变量
5. 正确地定义数组
6. 将局部环境变量提升为全局
7. 正确选择引号
8. 特殊变量名
三、运算符
1. 算术运算符
2. 逻辑运算符
3. 常用的特殊字符串
4. 正则表达式
5. 扩展的正则表达式
四、条件选择、判断
1. if
2. case
3. 循环
3.1 for
3.2 while循环
3.3 until
3.4 select循环与菜单
五、read 读取控制台输⼊
六、⾃定义函数
七、练习
一、介绍
Shell ⼀个命令解释器,它接收应⽤程序/⽤户命令,然后调⽤操作系统内核。
Shell是⼀个功能强⼤的编程语⾔,易编写、易调试、灵活性强。
1. Linux提供的Shell解析器
cat /etc/shells
vim hello.sh
chmod u+x hello.sh 设置权限
./hello.sh 或 sh hello.sh 或 bash hello.sh 控制台输出
2. bash和sh关系
软连接
3. Centos默认的Shell解析器是bash
echo $SHELL 环境变量
二、定义
1. 变量名的定义规则
(1)变量名称可以由字⺟、数字和下划线组成,但是不能以数字开头,环境变量名建议⼤写。
(2)等号两侧不能有空格
(3)在bash中,变量默认类型都是字符串类型,⽆法直接进⾏数值运算。
(4)变量的值如果有空格,需要使⽤双引号或单引号括起来。
2. 等号周围没有空格
username="小明"
echo $username
username="小 红"
username=小红
3. 查看变量
set 查看所有环境变量
4. 删除变量
unset username 删除变量username
5. 正确地定义数组
arr=("小旺财" "小猫猫" "小丫丫")
echo ${arr[1]} 查看下标为1的内容
echo ${arr[*]} 查看数组所有内容
6. 将局部环境变量提升为全局
export username 提升变量范围 (局部提升为全局)
7. 正确选择引号
(1)不加引号、单引号、双引号对纯字符串无影响,有空格要用引号
dog=金毛
dog='金毛'
dog="金毛"
echo $dog 输出金毛
(2)单引号和双引号的区别:
⼀对单引号内的字符串将始终被解释为它的本身。
yy='$dog 是一个小狗狗' 不解析$ 显示$dog
yy="$dog 是一个小狗狗" 对$解析 显示金毛
(3)反引号
kk=`ls` 或 kk=$(ls) 将命令的结果保存到变量中
echo $kk
8. 特殊变量名
vim demo2.sh echo $0 echo$1 echo $2
sh demo2.sh a b c 传参a、b、c 显示demo2.sh a b
$n:n为数字(0为脚本名称,1-9参数)
$#:获取所有输⼊参数个数,常⽤于循环。
$*:这个变量代表命令⾏中所有的参数,$*把所有的参数看成⼀个整体。
$@:这个变量也代表命令⾏中所有的参数,不过$@把每个参数区分对待。
$?:最后⼀次执⾏的命令的返回状态。如果这个变量的值为0,证明上⼀个命令正确执⾏;如果这个变量的值为⾮0(具体是哪个数,由命令⾃⼰来决定),则证明上⼀个命令执⾏不正确了。)
echo $# (获取所有输⼊参数个数)
echo $? 查看上一次命令或者脚本的执行状态的结果,如果是0,表示正确,如果是非0,表示错误
三、运算符
1. 算术运算符
echo $((3+2)) 或 echo $[10+20]
expr 3 + 2 加空格
\* 乘法用转义字符\
expr 3 \* 2
2. 逻辑运算符
格式:[ 条件 ]
注意:[] ⾥⾯前后必须要有空格
(1)字符串比较
[ 9 -lt 10 ] 9<10
echo $? 显示0,正确
-lt ⼩于(less than) -le ⼩于等于(less equal)
-eq 等于(equal) -gt ⼤于(greater than)
-ge ⼤于等于(greater equal) -ne 不等于(Not equal)
(2)文件权限判断
[ -r demo1.sh ] 验证demo1.sh有没有读权限
echo $? 显示0,有读权限
[ -x demo1.sh ] 验证demo1.sh有没有执行权限
(3)多条件判断
[ 9 -lt 10 ] && echo 对 正确会输出对
[ 9 -gt 10 ] && echo 对 错误不会输出对
3. 常用的特殊字符串
(1)^匹配⼀⾏的开头,如下,会匹配/etc/passwd中以root开头的⾏
grep "^root" /etc/passwd
(2)$匹配⼀⾏的结尾,如下,会匹配出/etc/passwd中以bash结尾的⾏
grep "bash$" /etc/passwd
(3).匹配⼀个任意字符
grep "r..t" /etc/passwd
(4)*不单独使⽤,他和上⼀个字符连⽤,表示匹配上⼀个字符0次或多次
grep "r*" /etc/passwd
4. 正则表达式
正则表达式通常被⽤来检索、 替换那些符合某个模式的⽂本。
echo "t1234567" | grep "[0-9]" 1234567标红
echo "t123p1234567" | grep "[0-9][3,6]" 23 23 56 标红
echo '123$456$789' | grep "$"
echo '123$456$789' | grep "\$" \表示转义
echo '123$456$789' | grep "\\$" 找出所有包含‘$’的⾏
5. 扩展的正则表达式
echo '1233333-45-6755668' | grep -E "[0-9]{2,3}" 0-9数字,出现2-3次标红(尽量满足多的)
四、条件选择、判断
1. if
age=$1
if [ $age -le 16 ];then
echo "他还是个孩子"
else
echo "他是个大人"
fi
if [ $1 -le 16 ];then
echo "他还是个孩子"
elif [ $1 -le 24 ] && [ $1 -gt 18 ];then
echo "他是个年轻人,不能太气盛"
else
echo "他是个大人"
fi
sh demo3.sh 13 他还是个孩子
sh demo3.sh 20 他是个年轻人,不能太气盛
sh demo3.sh 26 他是个大人
ctrl+q解锁
2. case
case $1 in
"上午")
echo "火锅"
echo "烤肉"
;;
"中午")
echo "三碗扯面"
echo "六个纯瘦夹馍"
;;
"晚上")
echo "燕窝莲子羹"
echo "牛奶"
;;
*)
echo "把时间填好"
esac
sh demo4.sh 上午 火锅 烤肉
sh demo4.sh 中午 三碗扯面 六个纯瘦夹馍
sh demo4.sh 晚上 燕窝莲子羹 牛奶
sh demo4.sh 白天 把时间填好 (默认)
注意事项:
1) case⾏尾必须为单词“in”,每⼀个模式匹配必须以右括号“)”结束。
2) 双分号“;;”表示命令序列结束,相当于java中的break。
3) 最后的“*)”表示默认模式,相当于java中的default。
3. 循环
3.1 for
s=0
for((i=0; i<=100;i++))
do
s=$[$s+$i]
done
echo $s
sh demo05.sh 输出5050
do相当于{ , done相当于}
for j in $*
do
echo $j
done
for j in $@
do
echo $j
done
sh demo6.sh aa bb cc 输出 aa bb cc aa bb cc
# $@ 最终会被""解析为一个数组,每个元素都是传入的参数
for j in "$@"
do
echo $j
done
# $* 最终会被""解析为一个连续的字符串,只有一个元素
for j in "$*"
do
echo $j
done
sh demo6.sh aa bb cc 输出 aa bb cc aa、bb、cc
3.2 while循环
num=$1
s=0
while [ $num -ge 0 ]
do
s=$[$num+$s]
num=$[$num-1]
done
echo $s
3.3 until
进⼊条件:循环条件为false ;退出条件:循环条件为true;刚好和while相反,所以不常⽤,⽤while就⾏。
num=$1
s=0
until [ $num -eq 0 ]
do
s=$[$num+$s]
num=$[$num-1]
done
echo $s
3.4 select循环与菜单
PS3="请输⼊你要选择的序号: "
select menu in ⽶饭 扯⾯ 包⼦ 稀饭 退出
do
case $REPLY in
1|4) #米饭或稀饭s
echo "$menu 价格是 15"
;;
2|3) #扯面或包子
echo "$menu 价格是 20"
;;
5) #
break
;;
*) #默认
echo "请你好好选"
esac
done
PS3 是 select 的提示符,⾃动⽣成菜单,选择5 break 退出循环
五、read 读取控制台输⼊
read(选项)(参数)
选项:
-p:指定读取值时的提示符;
-t:指定读取值时等待的时间(秒)。
read -p "请输入第一个数" num1
read -p "请输入第二个数" num2
echo "$num1 加上 $num2 的结果是 $[$num1+$num2]"
read -t 10 -p "请输入第一个数" num1 #10秒钟输入第一个数
read -t 10 -p "请输入第二个数" num2
echo "$num1 加上 $num2 的结果是 $[$num1+$num2]"
六、⾃定义函数
function func1()
{
read -p "请输入第一个数" num1
read -p "请输入第二个数" num2
echo "$num1 加上 $num2 的结果是 $[$num1+$num2]"
}
func1 #调用
七、练习
编写⼀个函数来计算输⼊的是不是⼀个质数
function func1()
{
read -p "请输入一个数" num1
is_prime=true
for ((i=2; i*i<=$num1; i++)) #sprt(num1)
do
if [ $(($num1%i)) -eq 0 ]; then
is_prime=false
break
fi
done
if [ $is_prime = true ]; then
echo "$num1 是质数"
else
echo "$num1 不是质数"
fi
}
func1
#!/bin/bash
function func1()
{
read -p "请输入一个数" num1
is_prime=true
for ((i=2; i*i<=$num1; i++))
do
if [ $(($num1%i)) -eq 0 ]; then
is_prime=false
break
fi
done
if [ $is_prime = true ]; then
echo "$num1 是质数"
else
echo "$num1 不是质数"
fi
}
while true; do
echo "请选择操作:"
echo "1. 检查一个数是否为质数"
echo "2. 退出程序"
read -p "请输入选项编号:" choice
case $choice in
1)
func1
;;
2)
echo "退出程序"
exit 0
;;
*)
echo "无效的选项,请重新选择。"
;;
esac
done