linux shell编程-bash的奇技淫巧
Posted foxgab
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了linux shell编程-bash的奇技淫巧相关的知识,希望对你有一定的参考价值。
本文主要讲bash脚本中容易出错和很少用但是用起来有意想不到效果的部分。
循环:
正常的for循环:
for i in a b c 1 2 3; do echo "$i" done
数字序列循环:
for i in `seq 100`; do echo "$i" done
其中的 `seq 100` 也可以换成 {1..100}
{开始..结尾}的这种形式可以表示连续的数列,可以从小到大也可以从大到小,但是可惜不像python的range()那样可以指定间隔量
C语言风格的for循环:
for (( i=1; i<100; i++ )); do echo "$i" done
数学计算
双括号“(())”还可以用于数学计算:
(( a=123+456 )) echo $a # 579
在双括号中,变量并不需要用$符号来引用,英文单词天然是变量。
变量:
间接引用:
a=b b=100 echo ${!a} # 100
效果等同于 eval echo \$$a
字符串操作
变量值的字符长度:
a="abcdefg" echo ${#a} # 7
变量值字符截取:
a="abcdefg" echo ${a:2} # cdefg echo ${a:2:3} # cde
变量值字符删除:(#为从头部开始匹配,%为从尾部匹配,支持通配符“?*”)
a="abdcdefgh" echo ${a#*d} # 删除字符串头部匹配“*d”的部分,通配符*代表匹配任意多个字符,一个#号代表通配符“*”保守匹配 # cdefgh echo ${a##*d} # 两个#号表示贪婪匹配 # efgh echo ${a%d*} # 同上,两个%时代表贪婪匹配 # abdc
a=b b="abcdefg" echo "${!a#abc}" # defg
可以同时支持间接引用和字符删除
变量赋值安全
用于赋值前检查是否已经定义或赋值。
unset a unset b b="" # a没有定义,b定义了但是空值 echo ${a-789} # 如果没定义,则表达式采用默认值789 # 789 echo ${a:-789} # 如果没定义或是空值,则表达式采用默认值789 # 789 echo ${b-789} # 如果没定义,则表达式采用默认值789,b定义了 # echo ${b:-789} # 如果没定义或是空值,则表达式采用默认值789 # 789 echo $a # 原变量并没有被赋值 # echo $b # 原变量并没有被赋值 # b=123 echo ${b-789} # 如果变量已经被赋值,则不改变原有值 # 123
unset a echo ${a=789} # 如果a没定义,则表达式采用默认值,并给a赋值 # 789 echo $a # 789 # a已经被赋值了 a="" echo ${a=789} # echo ${a:=789} # 加冒号:的作用和之前一样 # 789 echo $a # 789
前面讲了用“-”和“=”的,还有一种用“+”的,用于当变量已经被赋值的情况下采用默认值,举一反三,不赘述了。
位置变量
$0是文件名,$#代表参数个数,$1,$2等等表示执行该脚本或函数后面跟的位置参数,$1代表第一个参数,依次类推,需要注意的是,第9个以后的参数应该这么表示:
${10}
这表示第10个参数,必须用花括号括起来,否则就变成第1个变量后面加个字符“0”了。因为这个有的人以为第9个以后的位置变量就不可用了,是错的。
[email protected]和$*都表示所有的变量,但是区别是前者将每个作为一个字符串,是多个字符串的结合,而后者将所有变量组合成一个字符串,用空格分隔。
这样不同会在for循环里面造成使用的区别,在for循环里面,如果加上引号 for i in "[email protected]" 和 for i in "$*" 是不同的,前者还是会依次把参数代入循环,而后者会吧所有参数作为字符串一次性代入:
echo ‘ for i in "[email protected]"; do echo "$i" done for i in "$*"; do echo "$i" done ‘ > myscript.sh chmod 755 myscript.sh ./myscript.sh abc 123 def
结果是:
abc 123 def abc 123 def
那么[email protected]加引号和不加引号有区别么?
大部分情况下结果看起来是一样的,但会在某些情况下造成麻烦,因为for循环会用换行符“\n”和空格来拆分变量,所以如果调用脚本所带的参数中带有空格或者换行符,不加引号的时候会把这个参数拆开了依次代入,而加了引号就可以避免这种情况。
echo ‘ for i in "[email protected]"; do echo "$i" done for i in [email protected] ; do echo "$i" done ‘ > myscript.sh chmod 755 myscript.sh ./myscript.sh abc "123 def"
结果是:
abc 123 def abc 123 def
for循环使用数组
将数组的值依次代入循环,可以用${arr[@}和${arr[*]}这两种方法,区别和加引号的区别同上面位置参数的使用相同。
字符串匹配
shell的字符串匹配通常是这样的:
[ "abc" = "abc" ] echo $? # 0
若字符串相同则返回0,否则返回1。除了全匹配外,通过双方括号“[[]]”还可以用正则表达式匹配
[[ "abc234def" =~ ^abc[0-9]{3}[a-z]+$ ]] echo $? # 0
注意这里正则表达式不能用引号括起来,而且只支持基本的正则,不支持如“\b \S”之类的扩展。
原文地址:http://www.cnblogs.com/foxgab/p/6901782.html
如果觉得本文对您有帮助,请扫描后面的二维码给予捐赠,您的支持是作者继续写出更好文章的动力!
以上是关于linux shell编程-bash的奇技淫巧的主要内容,如果未能解决你的问题,请参考以下文章
linux虚拟机下bash shell编程,制作一个音乐播放器,可以实现用代码打开mp3文件吗?
linux学习19 shell脚本基础-bash脚本编程基础及配置文件
linux的shell编程中#!/bin/sh和$bash是啥意思?
linux的shell编程中#!/bin/sh和bash是啥意思?
linux shell编程bash编程shell教程bash教程shell文档bash文档shell脚本bash脚本教程第一部分:绪论