shell script中的case……esac判断
上个小节提到的『 if .... then .... fi 』对於变量的判断是以『比对』的方式来分辨的,如果符合状态就进行某些行为,并且透过较多层次 (就是 elif ...) 的方式来进行多个变量的程序码撰写,譬如 sh09.sh 那个小程序,就是用这样的方式来撰写的罗。好,那么万一我有多个既定的变量内容,例如 sh09.sh 当中,我所需要的变量就是 "hello" 及空字串两个,那么我只要针对这两个变量来配置状况就好了,对吧?那么可以使用什么方式来设计呢?呵呵~就用 case ... in .... esac 吧~,他的语法如下:
case $变量名称 in <==关键字为 case ,还有变量前有钱字号 "第一个变量内容") <==每个变量内容建议用双引号括起来,关键字则为小括号 ) 程序段 ;; <==每个类别结尾使用两个连续的分号来处理! "第二个变量内容") 程序段 ;; *) <==最后一个变量内容都会用 * 来代表所有其他值 不包含第一个变量内容与第二个变量内容的其他程序运行段 exit 1 ;; esac <==最终的 case 结尾!『反过来写』思考一下! |
要注意的是,这个语法以 case (实际案例之意) 为开头,结尾自然就是将 case 的英文反过来写!就成为 esac 罗!不会很难背啦!另外,每一个变量内容的程序段最后都需要两个分号 (;;) 来代表该程序段落的结束,这挺重要的喔!至於为何需要有 * 这个变量内容在最后呢?这是因为,如果使用者不是输入变量内容一或二时,我们可以告知使用者相关的资讯啊!废话少说,我们拿 sh09.sh 的案例来修改一下,他应该会变成这样喔:
[root@www scripts]# vi sh09-2.sh #!/bin/bash # Program: # Show "Hello" from $1.... by using case .... esac # History: # 2005/08/29 VBird First release PATH=/bin:/sbin:/usr/bin:/usr/sbin:/usr/local/bin:/usr/local/sbin:~/bin export PATH case $1 in "hello") echo "Hello, how are you ?" ;; "") echo "You MUST input parameters, ex> {$0 someword}" ;; *) # 其实就相当於万用字节,0~无穷多个任意字节之意! echo "Usage $0 {hello}" ;; esac |
在上面这个 sh09-2.sh 的案例当中,如果你输入『 sh sh09-2.sh test 』来运行,那么萤幕上就会出现『Usage sh09-2.sh {hello}』的字样,告知运行者仅能够使用 hello 喔~这样的方式对於需要某些固定字串来运行的变量内容就显的更加的方便呢!这种方式你真的要熟悉喔!这是因为系统的很多服务的启动 scripts 都是使用这种写法的,举例来说,我们 Linux 的服务启动放置目录是在 /etc/init.d/ 当中,我已经知道里头有个syslog 的服务,我想要重新启动这个服务,可以这样做:
/etc/init.d/syslog restart
重点是那个 restart 啦!如果你使用『 less /etc/init.d/syslog 』去查阅一下,就会看到他使用的是 case 语法,并且会规定某些既定的变量内容,你可以直接下达 /etc/init.d/syslog ,该 script 就会告知你有哪些后续接的变量可以使用罗~方便吧! ^_^
一般来说,使用『 case $变量 in 』这个语法中,当中的那个『 $变量 』大致有两种取得的方式:
- 直接下达式:例如上面提到的,利用『 script.sh variable 』的方式来直接给予 $1 这个变量的内容,这也是在 /etc/init.d 目录下大多数程序的设计方式。
- 互动式:透过 read 这个命令来让使用者输入变量的内容。
这么说或许你的感受性还不高,好,我们直接写个程序来玩玩:让使用者能够输入 one, two, three ,并且将使用者的变量显示到萤幕上,如果不是 one, two, three 时,就告知使用者仅有这三种选择。
[root@www scripts]# vi sh12.sh #!/bin/bash # Program: # This script only accepts the flowing parameter: one, two or three. # History: # 2005/08/29 VBird First release PATH=/bin:/sbin:/usr/bin:/usr/sbin:/usr/local/bin:/usr/local/sbin:~/bin export PATH echo "This program will print your selection !" # read -p "Input your choice: " choice # 暂时取消,可以替换! # case $choice in # 暂时取消,可以替换! case $1 in # 现在使用,可以用上面两行替换! "one") echo "Your choice is ONE" ;; "two") echo "Your choice is TWO" ;; "three") echo "Your choice is THREE" ;; *) echo "Usage $0 {one|two|three}" ;; esac |
此时,你可以使用『 sh sh12.sh two 』的方式来下达命令,就可以收到相对应的回应了。上面使用的是直接下达的方式,而如果使用的是互动式时,那么将上面第 10, 11 行的 "#" 拿掉,并将 12 行加上注解 (#),就可以让使用者输入参数罗~这样是否很有趣啊?
转自《鸟哥》的博客。