Linux Shell编程之二选择结构

简介:

Shell编程学习之二

一、bash的条件测试

    测试方法或者说测试书写:

test EXPR

[ EXPR ]

` EXPR `

    例如:测试变量 User_Name 的之是否为root

    test $User_Name="root"

    [ $User_Name == "root" ]

    [[ $User_Name == "root" ]


    根据比较时操作数的类型,测试类型分为:

测试类型 运算符 运算符所代表的意义 示例
整形测试

-gt -lt -ge -le 

-eq -ne

-gt 大于  -lt 小于

-ge 大于或等于  -le 小于或等于

-eq 等于  -ne 不等于

都是双目运算符:

[ $num -gt 3 ]

test $num -ne $sum

[[ $num -ne 0 ]]

字符测试 == =~ > < !=

== 等于   >大于    < 小

!= 不等于   =~ 模式匹配 

都是双目运算符:

[ $num == "root"]

test $num > $sum

[[ "$num" =~ /bin/bash$ ]]

这里注意 =~只能用 ` `去匹配,而且=~后面的PATTERN(模式)不能使用"",''等引用字符

-n -z

-z 测试文件内容是否为空,为空时真,不为空为假

-n 测试文件内容是否为不空,不空为真,空为假

单目运算符

[ -n "$file_name" ]

文件测试

-a|e -f -L|h -d

-b -c -S -p -s

-r -w -x -N

-a|e 测试文件存在

-f 测试文件为一般文件

-L|h 测试文件为软连接文件

-d 测试文件是否为目录

-b -c -p -S 测试文件为块设备、字符设备、管道文件、socket文件

-r -w -x 测试文件可读、可写、可执行

-s 测试文件为空文件

-N 测试文件Mtime新于Atime

都是单目运算符

[ -f "$file_name" ]

[[ -b "$file_name" ]]

test -x $file_name

-nt -ot

file1 -nt file2 file1的Mtime新于file2的Mtime 

file1 -ot file2 file1的Mtime旧于file2的Mtime 

双目运算符

[ file1 -nt "$file_name" ]

[[ $file1 -ot "$file_name" ]]


二、逻辑运算

    布尔运算:布尔运算的结果只有2中:真和假。

    常见的逻辑运算有:与 或 非 异或。与或非常用 && || ! 来表示。

    与的逻辑关系:

假 && 任意
真 && 真

     或的逻辑关系:

真 || 任意
假 || 假

    非的逻辑关系:


!假
!真

    异或的逻辑关系:相同为假,不同为真


三、选择

    bash中的选择语句通常有if,case。当然if,case在大多数情况下是可以相互转换的。

1)if选择语句

1、单分支if语句:

    if CONDITION;then

选择分支

    fi

2、双分支的if语句:

    if CONDITION;then

选择分支1

    else

选择分支2

    fi

3、多分支的if语句:

    if CONDITION1;then

选择分支1

    elif CONDITION2;then

选择分支2

    elif CONDITION3;then

选择分支3

    ...

    else

选择分支n

    fi

2)case语句

    语法格式:

        case 变量引用 in

        PATTERN1)

            分支1

            ;;

        PATTERN2)

            分支2

            ;;

        ...

        *)

        分支n

        ;;

        esac

    PATTERN:类同于文件名通配机制,但支持使用“|”表示或者

    a|b: a或者b

    *:匹配任意长度的任意字符

    ?: 匹配任意单个字符

    []: 指定范围内的任意单个字符


4、练习

写一个脚本,完成如下任务,其使用形式如下所示:

    script.sh {start|stop|restart|status}

其中:

    如果参数为空,则显示帮助信息,并退出脚本;

    如果参数为start,则创建空文件/var/lock/subsys/script,并显示“starting script successfully.”

    如果参数为stop,则删除文件/var/lock/subsys/script,并显示“Stop script successfully.”

    如果参数为restart,则删除文件/var/locksubsys/script并重新创建,而后显示“Restarting script successfully.”

    如果参数为status,那么:

    如果文件/var/lock/subsys/script存在,则显示“Script is running...”,否则,则显示“Script is stopped.”

    说明:script.sh是脚本文件名,在创建时,其名称可以自己随意定义,但如果其名称发生变量,上/var/lock/sussys/下的文件名也要随之而变;

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
[root@server scripts] # cat myhttpd
#!/bin/bash
#
# Description: 
# Version: 0.0.1
# Author: Alex
# Date: 2014-07-09
 
#判断参数个数,如果参数小于1,则提示用法并退出
if  [ $ # -lt 1 ];then
         echo  "Usage: `basename $0` {start|stop|restart|status}"
         exit  2
fi
#判断/var/lock/subsys是否存在,不存在则创建此目录
if  [ ! -d  /var/lock/subsys  ]; then
     /bin/mkdir  -p  /var/lock/subsys
fi
 
if  "$1"  ==  "start"  ]; then
#如果/var/lock/subsys/`basename $0`文件不存在,则创建,并显示启动成功;若存在则提示已启动
     [ !  -e  "/var/lock/subsys/`basename $0`"  ] &&  /bin/touch   "/var/lock/subsys/`basename $0`"  &&  echo  "Starting `basename $0` successfully."  \
     ||   echo  "`basename $0` is already start."
elif  "$1"  ==  "stop"  ]; then
#如果/var/lock/subsys/`basename $0`文件存在,则删除,并显示关闭成功;若不存在则显示关闭失败
     [ -e  "/var/lock/subsys/`basename $0`"  ] &&  /bin/rm  -f   "/var/lock/subsys/`basename $0`"  &&  echo   "Stop myhttpd successfully."  \
     ||  echo  -e  "Stopping myhttpd \033[31mFAILED\033[0m."
elif  "$1"  ==  "status"  ]; then
#如果/var/lock/subsys/`basename $0`文件存在,显示running;若不存在则提示stopd
     [ -e  "/var/lock/subsys/`basename $0`"  ] &&  echo  "`basename $0` is running..."  ||  echo  "`basename $0` is stopped."
else
     echo  "Usage: `basename $0` {start|stop|restart|status}"
fi

    上面的脚本也可以用case语句结合函数来实现。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
# 一般情况下,case与函数一起使用的居多。
 
#!/bin/bash
 
if  [ $ # -lt 1 ];then
         echo  "Usage: `basename $0` {start|stop|restart|status}"
         exit  2
fi
 
[ $UID - ne  0 ] &&  echo  "permission denied."  &&  exit  5
 
if  [ ! -d  /var/lock/subsys  ]; then
     /bin/mkdir  -p  /var/lock/subsys
fi
 
service_name=` basename  $0`
ser_path= "/var/lock/subsys/$service_name"
start() {
     if  [ !  -e  "$ser_path"  ]; then
        /bin/touch   "$ser_path" 
         echo  "Starting $service_name successfully."
     else 
         echo  "$service_name is already start."
     fi 
}
 
stop() {
     if  [ -e  "$ser_path"  ]; then
         /bin/rm  -f   "$ser_path"
         echo   "Stop $service_name successfully."
     else
         echo  -e  "Stopping $service_name \033[31mFAILED\033[0m."
     fi
}
 
status() {
     if  [ -e  "$ser_path"  ]; then
         echo  "$service_name is running..."
     else
         echo  "$service_name is stopped."
     fi
}
 
other() {
     echo  "Usage: $service_name {start|stop|restart|status}"
     exit  4
}
 
case  "$1"  in
   start)
     start
     ;;
   stop)
     stop
     ;;
   status)
     status
     ;;
   *)
     other
     ;;
esac


四、其他

1、组合条件测试:在多个条件间实现逻辑运算

    与:[ condition1 -a condition2 ]

    condition1 && condition2

    或:[ condition1 -o condition2 ]

    condition1 || condition2

    非:[ -not condition ]

    ! condition

2、bash编程之交互编程

    read 与用户交互进行 

        -p "prompt" 提示语句

        -t timeout 设置超时时间

3、exit

    程序退出语句,一般是 exit n 这样使用,n是错误状态值。

4、shift

    通常是shift n 这样使用,n是要踢掉的参数个数

1
2
3
4
5
6
7
8
9
10
11
12
[root@server scripts] # cat ./aboutshift 
#!/bin/bash
 
echo  $1
shift  #踢掉2个参数
echo  $1
shift  #踢掉3个参数
echo  $1
[root@server scripts] # ./aboutshift 1 2 3 4 5 6 7 8 9 10
1
3
6

    而shift真正的作用是,判断脚本参数的问题。例如:

写一个脚本,使用形式如下所示

    showifinfo.sh [-i INTERFACE|-a] [-v]

要求:

    1、-i或-a不可同时使用,-i用于指定特定网卡接口,-a用于指定所有接口;

        显示接口的ip地址

    2、使用-v,则表示显示详细信息

        显示接口的ip地址、子网掩码、广播地址;

    3、默认表示仅使用-a选项;

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
#!/bin/bash
#
# 通过这种方法来判断一个脚本的参数选项
 
verbose=0
allInterface=0
ifflag=0
 
while  [ $ # -ge 1 ]; do
     case  $1  in
     -a)
     allInterface=1
         shift  1
     ;;
      -i)
     ifflag=1
     interface= "$2"
    shift  2
     ;;
      - v )
     verbose=1
     shift
     ;;
      *)
     echo  "wrong option"
     exit  2
     ;;
      esac
done
 
[ $ifflag - eq  1 -a $allInterface - eq  1 ] &&  "Usage Error."  &&  exit  12
     
if  [ $allInterface - eq  1 || $ # -eq 0 ]; then
     if  [ $verbose - eq  1 ];  then
     ifconfig  grep  "inet addr:"
     else
     ifconfig  grep  "inet addr:"  awk  '{print $2}' 
     fi
fi
 
if  [ $ifflag - eq  1 ];  then
     if  [ $verbose - eq  1 ];  then
     ifconfig  $interface |  grep  "inet addr:"
     else
     ifconfig  $interface |  grep  "inet addr:"  awk  '{print $2}' 
     fi
fi     









本文转自 羊木狼 51CTO博客,原文链接:http://blog.51cto.com/guoting/1436505,如需转载请自行联系原作者
目录
相关文章
|
18天前
|
Web App开发 Java Linux
Linux之Shell基本命令篇
Linux之Shell基本命令篇
Linux之Shell基本命令篇
|
1月前
|
算法 Linux C++
【Linux系统编程】解析获取和设置文件信息与权限的Linux系统调用
【Linux系统编程】解析获取和设置文件信息与权限的Linux系统调用
29 0
|
1月前
|
存储 算法 Linux
【Linux系统编程】深入理解Linux目录扫描函数:scandir目录函数(按条件扫描目录
【Linux系统编程】深入理解Linux目录扫描函数:scandir目录函数(按条件扫描目录
39 0
|
1月前
|
存储 算法 Linux
【Linux系统编程】Linux 文件系统探究:深入理解 struct dirent、DIR 和 struct stat结构
【Linux系统编程】Linux 文件系统探究:深入理解 struct dirent、DIR 和 struct stat结构
45 0
|
1天前
|
消息中间件 关系型数据库 MySQL
Linux:开源之魅与编程之道
Linux:开源之魅与编程之道
9 1
|
9天前
|
监控 Shell 开发工具
Shell编程
Shell编程
|
16天前
|
存储 Shell Linux
【攻防世界】unseping (反序列化与Linux bash shell)
【攻防世界】unseping (反序列化与Linux bash shell)
|
18天前
|
Linux 开发者
Linux文件编程(open read write close函数)
通过这些函数,开发者可以在Linux环境下进行文件的读取、写入和管理。 买CN2云服务器,免备案服务器,高防服务器,就选蓝易云。百度搜索:蓝易云
85 4
|
19天前
|
Shell Linux
【Linux】12. 模拟实现shell
【Linux】12. 模拟实现shell
27 2
|
24天前
|
传感器 Linux API
嵌入式Linux串口编程简介
嵌入式Linux串口编程简介
19 1