shell基础知识记录
调式脚本的方式
# 调试整个脚本执行内容 sh -vx test.sh # 不加-v,只显示脚本中运行的代码,不显示注释信息 # 调试脚本语法是否有问题 sh -n test.sh # 调试脚本的一部分,将脚本中需要调试的部分用set -x和set +x包含起来 [root@head test]# cat test.sh #!/usr/bin/bash set -x a=123 echo ${a} set +x if [ $a ];then echo 111 fi
变量匹配的规则
# ${变量#匹配规则} 从头开始匹配,删除匹配到的最短部分 [root@head ~]# echo ${url} www.test.com.cn [root@head ~]# echo ${url#*t} est.com.cn # ${变量##匹配规则} 从头开始匹配,删除匹配到的最长部分 [root@head ~]# echo ${url##*t} .com.cn # ${变量%匹配规则} 从尾开始匹配,删除匹配到的最短部分 [root@head ~]# echo ${url%t*} www.tes # ${变量%匹配规则}从尾开始匹配,删除匹配到的最长部分 [root@head ~]# echo ${url%%t*} www.
变量替换的规则
# ${变量/旧字符串/新字符串} 替换其中的一个 [root@head ~]# echo ${test} aabbccdd [root@head ~]# echo ${test/a/1} 1abbccdd # ${变量//旧字符串/新字符串} 替换所有 [root@head ~]# echo ${test//a/1} 11bbccdd
参数相关
$* # 表示传递到shell脚本中的所有参数,如参数1 2 3, 则表示"1 2 3", 将所有参数收集为一个参数 $@ # 表示传递到shell脚本中的所有参数,如参数1 2 3,则表示"1" "2" "3", 将参数都收集起来,不改变参数的数量 $# # 表示传递到脚本中参数的个数 $0 # 表示执行脚本的文件名 $1 # 表示第一个参数,$2 $3以此类推 $$ # 表示当前脚本运行的进程ID号 $? # 仅表示上一次命令执行的状态,只有0表示正常执行,其他都表示错误执行
read获取参数和变量设置
# 后面的hobby即为标量的名称 [root@head test]# read -p "your hobby:" hobby your hobby:walking [root@head test]# echo $hobby walking # 常量 [root@head test]# a=123 [root@head test]# readonly a [root@head test]# a=111 -bash: a: readonly variable # 取消设置变量 [root@head test]# b=111 [root@head test]# echo $b 111 [root@head test]# unset b [root@head test]# echo $b
普通数组
# 申明普通数组 # 方式一: array1=("bob" "18" "teacher") # 方式二: array2=([0]="jack" [2]=20 [3]="worker") # 方式三 [root@head test]# array3[0]="alice" [root@head test]# array3[1]=22 [root@head test]# array3[2]="docter" # 查看数组 declare -a # 通过索引访问数组元素 echo ${array2[1]} # 正向索引 echo ${array2[-1]} # 负向索引
关联数组
# 申明关联数组 # 方式一: [root@head test]# declare -A info [root@head test]# info["name"]="bob" [root@head test]# info["age"]=18 [root@head test]# info["job"]="teather" # 方式二: [root@head test]# declare -A info3 [root@head test]# info3=(["name"]="bob" ["age"]=20 ["job"]="actor") # 查看关联数组 declare -A 访问关联数组 [root@head test]# echo ${info[*]} teather bob 18 [root@head test]# echo ${info["name"]} bob [root@head test]# echo ${info["age"]} 18
数组补充
# 查看数组元素 [root@head ~]# array1=("bob" 18 "actor") [root@head ~]# echo ${array1[*]} [root@head ~]# echo ${array1[@]} # 删除数组某个元素 [root@head ~]# unset array1[0] # 删除整个数组 [root@head ~]# unset array1 # 数组元素切片 [root@head ~]# array1=("bob" 18 "actor" "drinking" "male") [root@head ~]# echo ${array1[*]:1} # 获取从第一个元素往后的所有元素 18 actor drinking male [root@head ~]# echo ${array1[*]:1:3} # 获取从第一个元素往后的3个元素 18 actor drinking # 数组元素的替换 [root@head ~]# echo ${array1[*]/male/female} # 将male替换成female bob 18 actor drinking female [root@head ~]# echo ${array1[*]/*a*/test} # 将包含a的元素都替换成test bob 18 test drinking test # 数组元素的循环 [root@head ~]# for item in ${array1[*]} > do > echo $item > done bob 18 actor drinking male [root@head ~]# array2=(["name"]="bob" ["age"]=18 ["job"]="actor" ["hobby"]="drinking" ["gender"]="male") [root@head ~]# for item in ${array2[*]} > do > echo $item > done drinking actor male bob 18 [root@head ~]# for i in ${!array2[*]} # 获取到数组的所有索引 > do > echo $i ${array2[$i]} > done hobby drinking job actor gender male name bob age 18
获取变量的长度
[root@head test]# aa="this is a test" [root@head test]# echo ${#aa} 14 [root@head test]# echo $aa | wc -L 14 [root@head test]# echo $aa | awk '{print length}' 14 [root@head test]# expr length "$aa" 14
字符的切片
[root@head test]# echo $aa this is a test [root@head test]# echo ${aa:2} # 从第二个字符,往后的所有字符 is is a test [root@head test]# echo ${aa:2:4} # 从第二个字符,往后的4个字符 is i [root@head test]# echo ${aa::4} # 前面的4个字符 this
算数运算符
bc:支持浮点型运算
[root@head test]# echo `echo 1 + 1 | bc` 2 [root@head test]# echo `echo 6 % 5 | bc` 1 [root@head test]# echo `echo 6 \* 5 | bc` 30 [root@head test]# echo `echo 6 - 5 | bc` 1 [root@head test]# echo `echo "scale=2;5.0/3.0"|bc` # 设置保留两位小数 1.66
expr:不支持浮点型运算,且数字间要留有空格
[root@head test]# echo `expr 1 + 1` 2 [root@head test]# echo `expr 3 - 2` 1 [root@head test]# echo `expr 3 \* 3` 9 [root@head test]# echo `expr 6 / 5` 1 [root@head test]# echo `expr 6.0 / 5.0` expr: non-integer argument
$(()): 不支持浮点型运算
[root@head test]# echo $(( 1 + 1 )) 2 [root@head test]# echo $((1+1)) 2 [root@head test]# echo $((3-2)) 1 [root@head test]# echo $((3*3)) 9 [root@head test]# echo $((9/3)) 3 [root@head test]# echo $((9.0/3)) -bash: 9.0/3: syntax error: invalid arithmetic operator (error token is ".0/3")
$[]同$(())和expr:不支持浮点型运算
let不支持浮点型运算,且只能赋值,不能直接输出
[root@head test]# let 1+1 [root@head test]# let res=1+1 [root@head test]# echo $res 2 [root@head test]# let res=3-2 [root@head test]# echo $res 1 [root@head test]# let res=3*3 [root@head test]# echo $res 9 [root@head test]# let res=6/3 [root@head test]# echo $res 2 [root@head test]# let res=6.0/3 -bash: let: res=6.0/3: syntax error: invalid arithmetic operator (error token is ".0/3")
测试运算符
test和[]用法是一样的
[root@head test]# test ! -d /home [root@head test]# echo $? 1 [root@head test]# test -d /home [root@head test]# echo $? 0 [root@head test]# [ -d /home ] # 注意两边有空格,[[]]与[]类似,但是[[]]支持正则 [root@head test]# echo $? 0
字符串测试
# != 测试两个字符串不相等,注意符号两边也有空格 [root@head test]# [ "test" != "test" ] [root@head test]# echo $? 1 # == 测试两个字符串相等 [root@head test]# [ "test" == "test" ] [root@head test]# echo $? 0 # -z 字符串长度为0则为真 [root@head test]# [ -z "" ] [root@head test]# echo $? 0 [root@head test]# [ -z "test" ] [root@head test]# echo $? 1 # -n 字符串长度不为0则为真 [root@head test]# [ -n "" ] [root@head test]# echo $? 1 [root@head test]# [ -n "test" ] [root@head test]# echo $? 0
数值比较
# -eq 等于 [root@head test]# [ 3 -eq 4 ] [root@head test]# echo $? 1 # -ne 不等于 [root@head test]# [ 3 -ne 4 ] # -gt 大于 [root@head test]# [ 4 -gt 3 ] # -lt 小于 [root@head test]# [ 3 -lt 4 ] # -ge 大于等于 [root@head test]# [ 3 -ge 3 ] # -le 小于等于 [root@head test]# [ 3 -le 3 ]
(())使用的数值比较符号
[root@head test]# ((3<2)) [root@head test]# ((3>=2)) [root@head test]# ((3<=2)) [root@head test]# ((3==3)) [root@head test]# ((3>2)) && ((5>4)) [root@head test]# echo $? 0 [root@head test]# ((3>2)) || ((5<4)) [root@head test]# echo $? 0 [root@head test]# ((3>2 && 5>4)) [root@head test]# echo $? 0
浮点数的比较
bc的结果中1代表正确,0代表错误
[root@head test]# echo "1.2>1.0" | bc 1 [root@head test]# echo "1.2<1.0" | bc 0 [root@head test]# echo "1==1" | bc 1 [root@head test]# echo "1!=1" | bc 0
其他补充
# $()中执行命令,且可以嵌套 [root@head test]# $(echo hostname) [root@head test]# $(echo ls $(pwd)) # ()在子shell中运算 [root@head test]# (aaa=123) [root@head test]# echo $aaa