3-Shell
shell简介
- 把在终端运行的命令保存到文件中,这个文件就是shell程序,简单的说,shell编程就是Linux命令的逻辑化处理
- shell解释器
- bash,ash,ksh,sh等,默认使用bash
- echo $SHELL
- /bin/bash
- 内核<shell<应用程序
shell程序
- 扩展名.sh(非必须)
- #!/bin/bash
- 指定解释器
- 运行
- 作为可执行程序
- 先修改执行权限
- ./test.sh
- /root/test.sh
- 作为解释器参数
- 先修改执行权限
- /bin/bash test.sh
- 作为可执行程序
shell变量
-
命名规则
- 只能使用数字字母下划线,不能以数字开头
- 不能使用bash里的关键字
-
变量定义
-
name="sicong" echo $name num=10 echo ${num}
- 变量名外面的花括号是可选的,加不加都行,加花括号是为了帮助解释器识别变量的边界
-
-
只读变量
- readonly my_url
- 只读变量的值不能发生改变
- 下次登录清空
-
删除变量
- unset my_url
- unset 命令不能删除只读变量
字符串和数组
-
字符串
-
单引号/双引号
- 单引号中的任何字符都会原样输出,单引号字符串中的变量是无效的,两层单引号则还原
- 双引号:可以包含除了$、`、\、‘‘之外的任意字符
- 反斜线:转义特定的字符,如:&、*、^、等
-
拼接字符串
-
my_name="sicong" str1="hello, "$my_name" !" str2="hello, ${my_name} !"
- 注意str2必须使用双引号
-
-
获取字符串长度
-
str="abcdef" echo ${#str}
-
-
获取子字符串
-
str="1000phone is a good school" echo ${str:1:3}
- 从下标1开始,长度为3,起始下标为0
-
-
-
数组
-
规则
- bash只支持一维数组,不支持多维数组,并不限制数组的大小,数组中元素的下标从0开始
-
定义数组
- 数组名=(值1 值2 值3....)
-
读取数组中的元素
-
\#读取数组中的元素 echo ${arr1[2]} \#如果要读取数组中的全部元素 echo ${arr2[@]} \#或 echo ${arr2[*]}
-
注意{}的使用
-
-
获取数组元素的个数
-
length=${#arr1[@]} echo $length \# 或者 length=${#arr1[*]} echo $length
-
-
获取数组单个元素的长度
-
lengthn=${#arr1[3]} echo $lengthn
-
-
运算符
-
expr
- expr:是一款表达式计算工具,使用它能够完成表达式的求值操作
-
运算符
-
数值运算符
- + - * / %
- val=
expr 1 + 2
- 注意``内各个字符间的空格
- val=
- + - * / %
-
文件测试
-
-r file 可读 -w file 可写 -x file 可执行 -e file 是否存在 -s file 检测文件是否为空 -f file 是一个普通文件,并且有内容 -z 变量名 判断变量名是空字符串或者没有定义过 ! 取反 ! -z name 变量name的字符串长度非0
-
-
关系运算符
- []中,前后都需要空格
- -eq
- 数字相等
- -ne
- 数字不等
- -gt
- 大于
- -lt
- 小于
- -ge
- 大于等于
- -le
- 小于等于
- ==
- 字符串相等
- if [ $a == $b ] # 字符串相等
- 字符串相等
-
逻辑运算符
- && || !
- 与或非
- if [ 1 -lt 3 ] && [ 2 -lt 3 ];
- && || !
-
echo/printf/test命令
- echo
- 字符串的输出
- echo -e "OK! \n"
- -e 开启转义,\n 显示换行
- echo -e "OK! \c"
- -e 开启转义 \c 不换行
- echo -e "OK! \n"
- 字符串的输出
- printf
- printf 中使用格式化字符串,还可以制定字符串的宽度、左右对齐方式等
- printf "%-10s %-8s %-4s\n" 姓名 性别 体重kg
printf "%-10s %-8s %-4.2f\n" 思聪 男 65.4321- %s %d %f都是格式替换符
- -10s:指的是一个宽度为10的字符(-表示左对齐,没有则表示右对齐)
- test
- test 命令用于检查某个条件是否成立,它可以进行数值、字符和文件三个方面的测试
- 注意与[]的联系
- if test $[num1] -eq $[num2]
- test 命令用于检查某个条件是否成立,它可以进行数值、字符和文件三个方面的测试
shell中的流程控制语句
-
if语句
-
单分支
-
if [ 1 -lt 3 ] && [ 2 -lt 3 ]; then echo "ok" fi
-
注意if后的分号
-
-
双分支
- else
-
多分支
- elif
else
- elif
-
-
case语句
-
echo '输入 1 到 4 之间的数字:' read aNum case $aNum in 1) echo '你选择了 1' ;; 2) echo '你选择了 2' ;; 3) echo '你选择了 3' ;; 4) echo '你选择了 4' ;; *) echo '你没有输入 1 到 4 之间的数字' ;; esac
-
-
循环语句
- for循环
- for 条件
do
循环体
done
- for 条件
- for num in 1 2 3 4 5
- for x in $
- for i in $(cat a.txt)
- 一行
- for n in
- for循环
-
while循环
- while read line
do
echo $line
done < /path/to/file - 注意传值的方式
- while read line
函数
-
无参数无返回值
-
demo() { echo 'hello world' } #调用函数 demo
-
-
有返回值
- return \(((\)aNum+\(anotherNum)) \#用\)?接收
- 注意双括号
-
有参数有返回值
- arg 3 4
- 函数内$1表示参数1,$0表示程序名本身
- $#
- 传递到脚本的参数个数
- $*
- 与$@用法类似
- 用echo $?接收返回值
扩展
-
#source hello.sh 将代码读入父shell直接执行
或. hello.sh
相当于python中的import -
关联数组
-
类似python的字典
-
declare -A arr2=([name]=lotuslaw) echo ${arr2[name]} arr2[age]=10 # 赋值
-
-
echo $?
- #如果返回值为0,说明上一条执行成功
-
if [[ "$num" =~ [0-9]+ ]];then
- 注意使用正则匹配时,变量要用双引号
- 条件判断使用正则,用[[]]
- =~为匹配的意思
-
if [ -r $a.txt ]
-
if test -r a.txt
-
n=$(expr $n + 1)
- 循环赋值
-
$(( n + 1 ))
- 双层括号,内部变量无需加$
-
sh -x test.sh调试代码
-
ctrl v shift i esc
-
ping -c 2 www.baidu.com
echo $?- 返回两次
-
awk
- awk 模式 动作
- 模式可以使用正则,在'//'内部
- echo $i |awk -F'[ /]+' '/inet/ && $3 !~ /^127/ {print $3}'
- awk -F: '/^root/,/adm/ {print $0}' /etc/passwd
- $NF表示被分割的最后一个字段
- # -v让awk使用shell变量
# unip 只对连续重复的值进行处理
- awk 模式 动作
-
命令 2>/dev/null 1>a.txt
- 1表示标准正确输出
- 2表示标准错误输出
- 命令 &>/dev/null
-
vim末行模式
- :%s/待替换/替换/g
- g表示全局替换
- :%s/待替换/替换/g
-
sed
- sed 's/待替换/替换/g' passwd
- 交互,源文件不变
- sed -i 's/待替换/替换/g' passed
- 非交互,直接改变源文件
- sed 's/待替换/替换/g' passwd