条件判断是一个程序获得智能的基础,而Bourne Shell脚本则通过命令 [ 来模拟大多数编程语言中的条件表达式。

shell中支持的控制结构有:

(1) if then else fi

(2) for in do done

(3) while do done

这些关键字可以引导程序检查状态码 $?,从而实现控制。下面讲解这个命令如何模拟条件表达式。

文件/目录判断
[ -b FILE ] 如果 FILE 存在且是一个块特殊文件则为真。
[ -c FILE ] 如果 FILE 存在且是一个字特殊文件则为真。
[ -d DIR ] 如果 FILE 存在且是一个目录则为真。
[ -e FILE ] 如果 FILE 存在则为真。
[ -f FILE ] 如果 FILE 存在且是一个普通文件则为真。
[ -g FILE ] 如果 FILE 存在且已经设置了SGID则为真。
[ -k FILE ] 如果 FILE 存在且已经设置了粘制位则为真。
[ -p FILE ] 如果 FILE 存在且是一个名字管道(F如果O)则为真。
[ -r FILE ] 如果 FILE 存在且是可读的则为真。
[ -s FILE ] 如果 FILE 存在且大小不为0则为真。
[ -t FD ] 如果文件描述符 FD 打开且指向一个终端则为真。
[ -u FILE ] 如果 FILE 存在且设置了SUID (set user ID)则为真。
[ -w FILE ] 如果 FILE存在且是可写的则为真。
[ -x FILE ] 如果 FILE 存在且是可执行的则为真。
[ -O FILE ] 如果 FILE 存在且属有效用户ID则为真。
[ -G FILE ] 如果 FILE 存在且属有效用户组则为真。
[ -L FILE ] 如果 FILE 存在且是一个符号连接则为真。
[ -N FILE ] 如果 FILE 存在 and has been mod如果ied since it was last read则为真。
[ -S FILE ] 如果 FILE 存在且是一个套接字则为真。
[ FILE1 -nt FILE2 ] 如果 FILE1 has been changed more recently than FILE2, or 如果 FILE1 exists and FILE2 does not则为真。
[ FILE1 -ot FILE2 ] 如果 FILE1 比 FILE2 要老, 或者 FILE2 存在且 FILE1 不存在则为真。
[ FILE1 -ef FILE2 ] 如果 FILE1 和 FILE2 指向相同的设备和节点号则为真。

字符串判断
[ -z STRING ] 如果STRING的长度为零则为真 ,即判断是否为空,空即是真;
[ -n STRING ] 如果STRING的长度非零则为真 ,即判断是否为非空,非空即是真;
[ STRING1 = STRING2 ] 如果两个字符串相同则为真 ;
[ STRING1 != STRING2 ] 如果字符串不相同则为真 ;
[ STRING1 ]  如果字符串不为空则为真,与-n类似

数值判断
INT1 -eq INT2 INT1和INT2两数相等为真 ,=
INT1 -ne INT2 INT1和INT2两数不等为真 ,<>
INT1 -gt INT2 INT1大于INT1为真 ,>
INT1 -ge INT2 INT1大于等于INT2为真,>=
INT1 -lt INT2 INT1小于INT2为真 ,<
INT1 -le INT2 INT1小于等于INT2为真,<=

总之,“=”用于比较字符串;“-eq”用于比较整型数

复杂逻辑判断
-a 与
-o 或
! 非

1、如果a>b且a<c
if (( a > b )) && (( a < c ))
if [[ $a > $b ]] && [[ $a < $c ]]
if [ $a -gt $b -a $a -lt $c ]

2、如果a>b或a<c
if (( a > b )) || (( a < c ))
if [[ $a > $b ]] || [[ $a < $c ]]
if [ $a -gt $b -o $a -lt $c ]

"||"和"&&"在SHELL里可以用,第一个可以写成if [ a>b && a ]

双括号和双中括号的含义见下文中对各种括号的解释。

Shell中的括号(), (()), [], [[]]

1、单小括号 ()
①命令组。括号中的命令将会新开一个子shell顺序执行,所以括号中的变量不能够被脚本余下的部分使用。括号中多个命令之间用分号隔开,最后一个命令可以没有分号,各命令和括号之间不必有空格。
②命令替换。等同于`cmd`,shell扫描一遍命令行,发现了$(cmd)结构,便将$(cmd)中的cmd执行一次,得到其标准输出,再将此输出放到原来命令。注意花括号${}也可以被看做命令替换,但是两者有所区别,花括号内是定义好的变量,而不是shell命令。
③用于初始化数组。如:array=(a b c d)

2、双小括号 (( ))
①整数扩展。这种扩展计算是整数型的计算,不支持浮点型。((exp))结构扩展并计算一个算术表达式的值,如果表达式的结果为0,那么返回的退出状态码为1,或者 是"假",而一个非零值的表达式所返回的退出状态码将为0,或者是"真"。
②只要括号中的运算符、表达式符合C语言运算规则,都可用在$((exp))中。作不同进位(如二进制、八进制、十六进制)运算时,输出结果全都自动转化成了十进制。如:echo $((16#5f)) 结果为95 (16进位转十进制)。单纯用 (( )) 也可重定义变量值,比如 a=5; ((a++)) 可将 $a 重定义为6。双括号中的变量可以不使用$符号前缀。括号内支持多个表达式用逗号分开。
③甚至可以替代循环结构,只要括号中的表达式符合C语言运算规则。比如可以直接使用for((i=0;i<5;i++)), 如果不使用双括号, 则为for i in `seq 0 4`或者for i in {0..4}。再如可以直接使用if (($i<5)), 如果不使用双括号, 则为if [ $i -lt 5 ]。

3、单中括号 []
①标准命令 [ 和 test 是具有相同作用,区别在于 [ 命令的最后一个参数是 "]" 。
②在正则表达式中用于表示字符范围。作为test用途的中括号内不能使用正则。
④在一个array 结构的上下文中,中括号用来引用数组中每个元素的编号。

4、双中括号[[ ]]
①[[是 bash 程序语言的关键字,并不是一个命令。[[ ]] 结构比[ ]结构更加通用,不过注意[[ 依然要和中括号内的内容用空格隔开。
②支持字符串的模式匹配,使用=~操作符时支持正则表达式,使用==操作符时则支持通配符,字符串比较时可以把右边的作为一个模式,而不仅仅是一个字符串,比如[[ hello == hell? ]],结果为真。
③使用[[ ... ]]条件判断结构,而不是[ ... ],能够防止脚本中的许多逻辑错误。比如,&&、||、<和> 操作符能够正常存在于[[ ]]条件判断结构中,但是如果出现在[ ]结构中的话,会报错,原因是 [ 命令不能解释&&的含义。比如可以直接使用if [[ $a != 1 && $a != 2 ]], 如果使用单括号, 则为if [ $a -ne 1] && [ $a != 2 ]或者if [ $a -ne 1 -a $a != 2 ]。
④bash把双中括号中的表达式看作一个单独的元素,并返回一个退出状态码。

语法提醒:shell有时靠命令来模拟运算。例如四则运算可以借助:let, expr 等命令完成。如对变量 x 加 1 可以写作:let "x = $x + 1" 或者 x=`expr $x + 1‘ 。如果参数有空格,一定要用引号括起来才不会出错。空格在shell中是有意义的。

PS:注意shell中,所有的输入都是字符串类型(当然任何语言都是如此,只是shell支持的类型解释和转换比较少),其中美元符$ 反引号` 反斜线\ 都被sh进程或者bash进程解释成字符串替换或命令替换,也就是用特定的输出字符串替换原命令,然后再继续执行新的命令。

调试:

查看shell脚本的执行过程
在执行的时候,通过下面的方式:
#sh -x test.sh

获取命令行参数:

注意 $ 是一个被解释成命令替换的符号,和反引号有类似之处。

$# 是传给脚本的单词个数
$0 是脚本本身的名字
$1 是传递给该shell脚本的第一个单词
$2 是传递给该shell脚本的第二个单词
$@ 是传给脚本的所有单词组成的列表数据结构
$* 将被替换成一个被包括在引号内的字符串,以一个单字符串显示所有向脚本传递的参数,与位置变量不同,参数可超过9个
$$ 是脚本运行的当前进程ID号
$? 是显示最后命令的退出状态,0表示没有错误,其他表示有错误

shell文本处理

重点掌握三个命令:find, grep, sed, awk,也就实现了对文本的增(插入)、删、改(替换)、查

1、find命令用于查找文件,如:

xin$ sudo find / -type f -size +1G

-name   filename             #查找名为filename的文件

用于查找磁盘上大于1G的文件。

2、grep命令用于查找文本,格式为:

grep <pattern> <filename>

3、sed命令用于编辑文本文件,最基本的命令当然是插入和删除,格式为:

sed [options] 'command' file(s) 注意用单引号而不是双引号,\ $ ` 等才不会被shell解释成字符串替换标志,而会直接把字面值转交给sed解释。

options:

-i :直接修改读取的文件内容,而不是将程序的结果输出到终端。

command:

格式 [n1,[n2]] function 其中 n1 和 n2 表示目标文本的首行行号和尾行行号

function:

a :新增, a 的后面可以接字串,而这些字串会在新的一行出现(目前的下一行)
c :取代, c 的后面可以接字串,这些字串可以取代 n1,n2 之间的行
d :删除,因为是删除啊,所以 d 后面通常不接任何字符串
i :插入, i 的后面可以接字串,而这些字串会在新的一行出现(目前的上一行)
p :列印,亦即将某个选择的数据印出。通常 p 会与参数 sed -n 一起运行
s :替换,可以直接进行取代的工作,通常这个 s 的动作可以搭配正规表示法,例如 1,20s/old/new/g

$:代表最后一行

示例:

替换:

Linux格式为:sed -i "s/192.168.0.2/192.168.0.3/g" *.rptdesign

Mac格式为:sed -i "" "s/192.168.0.2/192.168.0.3/g" *.rptdesign 相当于需要一个备份文件

删除:

sed -i "" '/^abc/d' ~/tmp/tmp.txt

插入:

sed -i "" '/192/a\
abc
' ~/tmp/tmp.txt

管道

示例: $ find .  | xargs svn add --force *.*

xargs命令会把从管道中获得的输入拆分,逐个作为下一个命令的输入。

Bourne Shell:控制语句、条件判断、文本处理、常用命令的更多相关文章

  1. 我们一起来学Shell - shell的条件判断

    文章目录 Shell 条件测试语法 符号说明 Shell 测试表达式 文件测试表达式 字符串测试表达式 整数操作符 逻辑操作符 测试表达式的区别总结 Shell 条件判断之if语句 单分支 IF 条件 ...

  2. shell中条件判断if中的-z到-d的意思

    shell中条件判断if中的-z到-d的意思 [ -a FILE ] 如果 FILE 存在则为真. [ -b FILE ] 如果 FILE 存在且是一个块特殊文件则为真. [ -c FILE ] 如果 ...

  3. Linux shell if条件判断2

    前面介绍linux shell的if判断的语法,现在再补充一点. Linux shell if条件判断1 分支判断结构     if , case   下面两个结构语法,已经在前面有过示例. 结构1: ...

  4. shell中条件判断if中的-z到-d

    shell中条件判断if中的-z到-d的意思 [ -a FILE ] 如果 FILE 存在则为真. [ -b FILE ] 如果 FILE 存在且是一个块特殊文件则为真.[ -c FILE ] 如果 ...

  5. shell test条件判断

    test 条件判断 # 符号 [ ] 等同  test命令 test -lt # 判断大小 echo $? # 查看上句test命令返回状态 # 结果0为真,1为假 test -n "hel ...

  6. linux文本处理常用命令

    linux文本处理常用命令   linux文本处理命令:grep.sed.printf.awk 1.grep grep的作用是按行查找字符,输出包含字符的行. #从文件查询 grep 'hello' ...

  7. Shell IF条件判断解析

    IF条件判断 1.基本语法: if [ command ]; then #符合该条件执行的语句 fi2.扩展语法: if [ command ];then #符合该条件执行的语句 elif [ com ...

  8. 第十三章、学习 Shell Scripts 条件判断式

    利用 if .... then 单层.简单条件判断式 if [ 条件判断式 ]; then 当条件判断式成立时,可以进行的命令工作内容: fi <==将 if 反过来写,就成为 fi !结束 i ...

  9. Linux之shell编程条件判断-if,while,for,case

    if 语法格式 if condition then statements [elif condition then statements] [else statements ] fi 示例 vi if ...

  10. shell中条件判断语法与判断条件小结

    1. IF条件判断语法: if Athen   dosthelif B   dosthelse   dosthfi 2. 判断条件:   2.1 字符串判断   str1 = str2 当两个串有相同 ...

随机推荐

  1. 【转】MongoDB 3.0 正式版本即将发布,强力推荐

    MongoDB 今天宣布3.0 正式版本即将发布.这标志着 MongoDB 数据库进入了一个全新的发展阶段,提供强大.灵活而且易于管理的数据库管理系统. MongoDB 3.0 在性能和伸缩性方面都有 ...

  2. 【python】venv使用

    virtualenvwrapper 比 virualenv 好用一些. 准备 export WORKON_HOME=~/venv source /usr/bin/virtualenvwrapper.s ...

  3. Visio2010建立ER图并直接导出为SQL语句

    Visio2010建立ER图并直接导出为SQL语句 2013年08月20日 ⁄ 综合 ⁄ 共 2581字 ⁄ 字号 小 中 大 ⁄ 评论关闭 建立数据库时我们需要考虑数据之间的关系,为了理清数据之间的 ...

  4. javascript 与vbscript 互相调用

    在 VBScript 的function 中可以直接编写 javascript 代码 但是只能返回一个字符串给变量 <html><head> <script type=& ...

  5. 第9课 函数重载分析(下)与C、C++相互调用

    重载与指针 下面的函数指针将保存哪个函数的地址: 在给p赋值的时候,我们使用了func,但是这里并没有指明参数,编译器是怎么知道这个func函数指的是第一个func函数呢? 函数重载遇上指针: 将重载 ...

  6. Java第二次作业--数组和String类

    Deadline: 2017-3-28 23:00 一.学习要点 认真看书并查阅相关资料,掌握以下内容: 掌握基本数据类型和引用数据类型的区别 理解对象的生成与引用的关系 掌握构造方法的重载 掌握St ...

  7. 20155318 2016-2017-2 《Java程序设计》第八学习总结

    20155318 2016-2017-2 <Java程序设计>第八学习总结 教材学习内容总结 学习目标 了解NIO 会使用Channel.Buffer与NIO2 会使用日志API.国际化 ...

  8. [LOJ535]「LibreOJ Round #6」花火

    loj description 给你一个排列\(h_i\),你需要交换任意两个位置上的数使得交换后排列的逆序对数最少. \(n \le 3\times 10^5\) sol 首先可以发现,如果交换两个 ...

  9. Layui Table 分页记忆选中

    Layui Table 分页记忆选中 挺好的功能,之前为什么放弃了,哈哈哈! 在最早的版本中,layui 的 table 会记录每页的勾选状态,但很多用户反馈这是 bug,因为当他们获取选中数据时,其 ...

  10. FT5X06 如何应用在10寸电容屏

    硬件搭起来看现象,如下图: 红色区域是FT5406上报有效数据的范围(1280*600),以左上角为原点 ,X轴方向上报数据的最大值1280,Y轴方向上报的最大数据是600..但是我用的LG的10.1 ...