shell基礎(chǔ)(三)函數(shù)

一、函數(shù)

function 函數(shù)名(){
    指令蔗崎。。
    return n
}

以上可以簡寫成:
函數(shù)名(){
    指令..
    return n
}

二扰藕、函數(shù)的執(zhí)行

一:不帶參數(shù)的執(zhí)行
1.function和后面的小括號都不帶嗎缓苛,僅僅時函數(shù)名就可以執(zhí)行
2.函數(shù)的定義必須在執(zhí)行之前定義或加載(即先定義后執(zhí)行)
3.函數(shù)執(zhí)行時,會和腳本公用變量邓深,也可以為函數(shù)設(shè)定局部變量及特殊位置參數(shù)
4.函數(shù)中的return和腳本中的exit功能類似未桥,return用來退出函數(shù),exit是用來退出腳本
5.return的返回值會給調(diào)用函數(shù)的程序芥备,而exit的返回值給執(zhí)行程序的shell
6.如果講函數(shù)獨立與腳本之外冬耿,被腳本加載使用時,需要使用source或者"."來提前加載使用
  例如:
        . /etc/init.d/functions  #加載系統(tǒng)函數(shù)中的命令或者參數(shù)變量萌壳,以供后面的程序使用
7.local定義函數(shù)內(nèi)部的局部變量亦镶,變量在離開函數(shù)后會消失

二:帶參數(shù)的執(zhí)行:
  函數(shù)名 參數(shù)1 參數(shù)2
1.shell的位置參數(shù)$1日月、$2、..$# 缤骨、$*山孔、$?及$@都可以作為函數(shù)的參數(shù)使用,此時荷憋,父腳本的參數(shù)臨時被隱藏,而$0仍然時父腳本的名稱
2.當函數(shù)執(zhí)行完成時台颠,原來的命令行腳本的參數(shù)恢復
3.函數(shù)的參數(shù)變量是在函數(shù)體里面定義的

小插曲

1.使用cat命令追加多行,如打印選項菜單
cat <<END
    1.FIRST
    2.SECOND
    3.THIRD 
END

2.給輸出的字體加顏色
echo -e 識別轉(zhuǎn)義字符,這里識別字符的特殊含義勒庄,加顏色

 #顏色的開始
 RED_COLOR='\E[1;31m'
 GREEN_COLOR='\E[1;32m'
 YELLOW_COLOR='\E[1;33m'
 BLUE_COLOR='\E[1;33m'

 #顏色的結(jié)束
 RES='\E[0m'
  
 echo -e ${RED_COLOR} OLD ${RES}  #OLD是紅色
 echo -e ${GREEN_COLOR} OLD ${RES} #OLD是綠色
 echo -e ${YELLOW_COLOR} OLD ${RES} #OLD是黃色
 echo -e ${BLUE_COLOR} OLD ${RES} #OLD是藍色

實戰(zhàn)題目一:

用shell腳本檢查某網(wǎng)站是否存在異常

方式一(普通):
#!/bin/bash
 if [ $# -ne 1 ];then
        usage $"usage $0 url"
 fi
wget --spider -q -o /dev/null --tries=1 -T 5 $1 
#--spider用于測試串前,不下載,-q不在命令中顯示 -o 輸入到后面的文件中 实蔽,--tries=number為嘗試次數(shù)和-t一樣  -T超時時間和--timeout一樣 -S顯示響應頭
if [ $? -eq 0 ];then
        echo "ok"
else
        echo "error"
fi
方式二(函數(shù)封裝):
#!/bin/bash
function Usage(){

        echo $"Usage:$0 url"
        exit 1
}
function check_url(){
        wget --spider -q -o /dev/null -t 1 -T 5 $1 
        if [ $? -eq 0 ];then
                echo "ok"
        else
                echo "error"
        fi 
}
function main(){
        if [ $# -ne 1 ];then
                Usage
        else
                check_url $1
        fi
}
main $*  #將腳本傳入的參數(shù)全部都傳到主函數(shù)中

實戰(zhàn)題目二:參數(shù)傳入腳本荡碾、檢查某網(wǎng)站是否存在異常,以更專業(yè)的方式輸出

#!/bin/bash
. /etc/init.d/functions  #調(diào)用(加載)系統(tǒng)函數(shù),因為下面要用action函數(shù)
function Usage(){
        echo $"usage:$0 url"
        exit 1
}
function check_url(){
        wget --spider -q -o /dev/null -t 1 -T 5 $1
        if [ $? -eq 0 ];then
                action "test $1" /bin/true
        else
                action "test $1" /bin/false
        fi
}
function main (){
        if [ $# -ne 1 ];then
                Usage
        else
                check_url $1
        fi
}
main $*

效果如下:
[root@mycentos shell]# sh 3.sh www.baidu.com   
test www.baidu.com                                         [  OK  ]
[root@mycentos shell]# sh 3.sh www.baidu.c
test www.baidu.c                                           [FAILED]

實戰(zhàn)題目三:用shell開發(fā)模塊化rsync服務啟動腳本

#!/bin/bash
#chkconfig:2345 21 81
#description
#上面2行是將rsync加入開機自啟動服務

#調(diào)用系統(tǒng)函數(shù)
. /etc/init.d/functions


#輸入錯誤提示
function Usage(){
        echo $"usage $0 {start|stop|restart}"
        exit 1
}


#啟動服務
function Start(){
        rsync --daemon  #啟動服務
        sleep 2    #啟動服務2秒后再做判斷

        if [ $(netstat -pantu | grep rsync | wc -l) -ne 0 ];then
                action "rsyncd is started" /bin/true
        else
                action "rsyncd is started" /bin/false
        fi
}
#停止服務
function Stop(){

        killall rsync&>/dev/null

        sleep 2

        if [ $(netstat -apntu| grep rsync | wc -l) -eq 0 ];then
                action "rsyncd is stopped" /bin/true
        else
                action "rsyncd is stopped" /bin/false
        fi
}

case "$1" in
 "start")
        Start
        ;;
 "stop")
        Stop
        ;;
 "restart")
        Stop
        sleep 1
        Start
        ;;
  *)
        Usage
esac

結(jié)果如下:
[root@mycentos init.d]# /etc/init.d/rsyncd start
rsyncd is started                                          [  OK  ]
[root@mycentos init.d]# lsof -i:873
COMMAND  PID USER   FD   TYPE DEVICE SIZE/OFF NODE NAME
rsync   1478 root    4u  IPv4  13067      0t0  TCP *:rsync (LISTEN)
rsync   1478 root    5u  IPv6  13068      0t0  TCP *:rsync (LISTEN)
[root@mycentos init.d]# /etc/init.d/rsyncd stop
rsyncd is stopped                                          [  OK  ]
[root@mycentos init.d]# lsof -i:873
[root@mycentos init.d]# /etc/init.d/rsyncd restart
rsyncd is stopped                                          [  OK  ]
rsyncd is started                                          [  OK  ]
[root@mycentos init.d]# lsof -i:873               
COMMAND  PID USER   FD   TYPE DEVICE SIZE/OFF NODE NAME
rsync   2379 root    4u  IPv4  19734      0t0  TCP *:rsync (LISTEN)
rsync   2379 root    5u  IPv6  19735      0t0  TCP *:rsync (LISTEN)

注:
1.在安裝或者啟動時局装,如果遇到找不到“/etc/rsync.conf”文件時坛吁,要用touch建立一個,實際工作中要寫入東西铐尚,此處為了方便就不寫拨脉,為了啟動rsync服務即可
2.rsync具體的脫離xinetd啟動的方式見"shell基礎(chǔ)二"
3.放在/etc/init.d目錄下就可以用service命令啟動,啟動前需要是腳本有執(zhí)行權(quán)限宣增,否則無法執(zhí)行玫膀,也無法自動補全。
4.要加入開機自啟動爹脾,則需要加如腳本中解釋器下面2行帖旨,然后“chkconfig --add rsyncd”加入自啟動 "rsyncd"是/etc/init.d目錄下的服務名稱

實戰(zhàn)四:執(zhí)行shell腳本,打印如下菜單灵妨,柑橘選擇解阅,給選擇的水果加一種顏色。

1.紅色的蘋果
2.綠色的蘋果
3.黃色的蘋果
4.藍色的蘋果

方法一(普通版)
#!/bin/sh

#定義好顏色泌霍,方便后面使用
RED_COLOR='\E[1;31m'
GREEN_COLOR='\E[1;32m'
YELLOW_COLOR='\E[1;33m'
BLUE_COLOR='\E[1;34m'

RES='\E[0m'

cat <<END
====================
        1.紅色的蘋果
        2.綠色的蘋果
        3.黃色的蘋果
        4.藍色的蘋果
====================
END

read -p "input a munber you want:" NUM

case "$NUM" in
  1)
        echo -e ${RED_COLOR}apple${RES}
        ;;
  2)
        echo -e ${GREEN_COLOR}apple${RES}
        ;;
  3)
        echo -e ${YELLOW_COLOR}apple${RES}
        ;;
  4)
        echo -e ${BLUE_COLOR}apple${RES}
        ;;
  *)
        echo "usage:input {1|2|3|4}"
        exit 1
esac
方法二(函數(shù)封裝):
#!/bin/sh

#定義好顏色货抄,方便后面使用
RED_COLOR='\E[1;31m'
GREEN_COLOR='\E[1;32m'
YELLOW_COLOR='\E[1;33m'
BLUE_COLOR='\E[1;34m'

RES='\E[0m'

function Menu(){
cat <<END
====================
        1.紅色的蘋果
        2.綠色的蘋果
        3.黃色的蘋果
        4.藍色的蘋果
====================
END
}
function Usage(){

        echo "$usage:input a number{1|2|3|4}"
        exit 1
}
function Choose(){
read -p "input a munber you want:" NUM
case "$NUM" in
  1)
        echo -e ${RED_COLOR}apple${RES}
        ;;
  2)
        echo -e ${GREEN_COLOR}apple${RES}
        ;;
  3)
        echo -e ${YELLOW_COLOR}apple${RES}
        ;;
  4)
        echo -e ${BLUE_COLOR}apple${RES}
        ;;
  *)
        Usage
esac
}
function Main(){
        Menu
        Choose
}
Main             

效果如圖:


image.png

實戰(zhàn)五:緊接著上題,請開發(fā)一個給制定內(nèi)容加上制定顏色的腳本

#!/bin/bash

RED_COLOR='\E[1;31m'
GREEN_COLOR='\E[1;32m'
YELLOW_COLOR='\E[1;33m'
BLUE_COLOR='\E[1;34m'

RES='\E[0m'

function Usage(){

        echo $"usage:$0 txt {red|green|yellow|pink}"
        exit 1
}

if [ $# -ne 2 ];then
           Usage
           exit
fi 
function Choose(){

        case "$2" in
                "red")
                        echo -e ${RED_COLOR}$1${RES}
                        ;;
                "green")
                        echo -e ${GREEN_COLOR}$1${RES}

                        ;;
                "yellow")
                        echo -e ${YELLOW_COLOR}$1${RES}
                        ;;
                "blue")
                        echo -e ${BLUE_COLOR}$1${RES}
                        ;;
                *)
                Usage
        esac
}
function Main(){
        Choose $1 $2
}
Main $*
注:
1.將參數(shù)二的顏色付給參數(shù)一
2.精確匹配單詞的三種方式
  1.grep -w 'oldboy' file 
  2.grep "\boldboy\b" file
  3.grep "^oldboy$" file
以上都是將出現(xiàn)oldboy單詞的行顯示出來烹吵,而不是將包含oldboy的行顯示出來

實戰(zhàn)五:

啟動Nginx服務的命令:/application/nginx/sbin/nginx
關(guān)閉Nginx服務的命令:/application/nginx/sbin/nginx -s stop

請開發(fā)腳本碉熄,以實現(xiàn)Nginx服務啟動和關(guān)閉功能,具體腳本命令為/etc/init.d/nginxd {start|stop|restart},并通過chkconfig進行開機自啟動

思路:
1.判斷開啟或關(guān)閉服務(一是檢測pid文件是否存在肋拔,存在就是開啟锈津,不存在就是服務已經(jīng)關(guān)閉),或者使用netstat鏈接數(shù)也可以
2.start和stop分別構(gòu)成函數(shù)
3.對函數(shù)和命令運行的返回值進行處理
4.chkconfig實現(xiàn)服務自啟動
代碼:
#!/bin/sh
#chkconfig:2345 27 83
#description

source /etc/init.d/functions  #加載系統(tǒng)函數(shù)庫

#定義文件路徑
PATH="/application/nginx/sbin"
PID_PATH="/application/nginx/logs/nginx.pid"
REVEAL=0
function Usage(){
        echo $"usage:$0 {start|stop|restart}"
        exit 1
}
#判斷參數(shù)的個數(shù)
if [ $# -ne 1 ];then
        Usage
fi
#開始函數(shù)
function Start(){
        if [ ! -f $PID_PATH ];then  #若原來服務是關(guān)閉的
                $PATH/nginx  #開啟服務
                REVEAL=$?  

                if [ $REVEAL -eq 0 ];then  #判斷是否開啟
                        action "nginx is started" /bin/true

                else
                        action "nginx is started" /bin/false
                fi

        else
                echo "nginx is running"

        fi
        return $REVEAL
}
function Stop(){#結(jié)束函數(shù)

        if [ -f $PID_PATH ];then  #若原來服務是啟動的
                $PATH/nginx -s stop  #關(guān)閉服務
                REVEAL=$?

                if [ $REVEAL -eq 0 ];then  #判斷是否關(guān)閉
                        action "nginx is stopped" /bin/true
                else
                        action "nginx is stopped" /bin/false
                fi
                return $REVEAL
        else
                echo "nginx is no running"
        fi
        return $REVEAL
}

        case "$1" in
           "start")
                 Start
                REVEAL=$?
                ;;
           "stop")
                Stop
                REVEAL=$?
                ;;
           "restart")
                Stop
                Start
                REVEAL=$?
                ;;
                *)
                Usage
        esac

 exit $REVEAL

效果如下:

[root@mycentos init.d]# /etc/init.d/nginxd start
nginx is running
[root@mycentos init.d]# /etc/init.d/nginxd stop
nginx is stopped                                           [  OK  ]
[root@mycentos init.d]# /etc/init.d/nginxd start
nginx is started                                           [  OK  ]
[root@mycentos init.d]# lsof -i:80
COMMAND  PID  USER   FD   TYPE DEVICE SIZE/OFF NODE NAME
nginx   2928  root    6u  IPv4  23795      0t0  TCP *:http (LISTEN)
nginx   2929 nginx    6u  IPv4  23795      0t0  TCP *:http (LISTEN)
[root@mycentos init.d]# /etc/init.d/nginxd restart
nginx is stopped                                           [  OK  ]
nginx is started                                           [  OK  ]
[root@mycentos init.d]# lsof -i:80                
COMMAND  PID  USER   FD   TYPE DEVICE SIZE/OFF NODE NAME
nginx   2940  root    6u  IPv4  24824      0t0  TCP *:http (LISTEN)
nginx   2941 nginx    6u  IPv4  24824      0t0  TCP *:http (LISTEN)

彩蛋一枚

return :
    1.用來退出函數(shù)凉蜂,后面的函數(shù)里面的內(nèi)容不再執(zhí)行
exit:
     2.用來退出腳本琼梆,后面的內(nèi)容不再執(zhí)行

function test(){
  return 1
}  
test    #函數(shù)執(zhí)行完成后性誉,$?會得到test中return后面的返回值
ls -l ./  #這條命令執(zhí)行成功,$?變成0
function test2(){
  exit 99
} 
test2 #函數(shù)執(zhí)行完成后茎杂,$?變成99,也就是exit后面的數(shù)值
$?的值會不斷的改變错览,有別于其他語言的函數(shù)調(diào)用的返回值。

結(jié)果:

#!/bin/bash
function test(){
        return 8
}
echo $?  #0
test
echo $? #8
function test2(){
        return 9
}
echo $? #0
test2
echo $? #9
ls -l ./
echo $? #0
exit 10

此shell執(zhí)行結(jié)束后煌往,echo $? 結(jié)果是10
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末倾哺,一起剝皮案震驚了整個濱河市,隨后出現(xiàn)的幾起案子刽脖,更是在濱河造成了極大的恐慌羞海,老刑警劉巖,帶你破解...
    沈念sama閱讀 212,816評論 6 492
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件曲管,死亡現(xiàn)場離奇詭異却邓,居然都是意外死亡,警方通過查閱死者的電腦和手機院水,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 90,729評論 3 385
  • 文/潘曉璐 我一進店門腊徙,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人檬某,你說我怎么就攤上這事撬腾。” “怎么了橙喘?”我有些...
    開封第一講書人閱讀 158,300評論 0 348
  • 文/不壞的土叔 我叫張陵时鸵,是天一觀的道長。 經(jīng)常有香客問我厅瞎,道長,這世上最難降的妖魔是什么初坠? 我笑而不...
    開封第一講書人閱讀 56,780評論 1 285
  • 正文 為了忘掉前任和簸,我火速辦了婚禮,結(jié)果婚禮上碟刺,老公的妹妹穿的比我還像新娘锁保。我一直安慰自己,他們只是感情好半沽,可當我...
    茶點故事閱讀 65,890評論 6 385
  • 文/花漫 我一把揭開白布爽柒。 她就那樣靜靜地躺著,像睡著了一般者填。 火紅的嫁衣襯著肌膚如雪浩村。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 50,084評論 1 291
  • 那天占哟,我揣著相機與錄音心墅,去河邊找鬼酿矢。 笑死,一個胖子當著我的面吹牛怎燥,可吹牛的內(nèi)容都是我干的瘫筐。 我是一名探鬼主播,決...
    沈念sama閱讀 39,151評論 3 410
  • 文/蒼蘭香墨 我猛地睜開眼铐姚,長吁一口氣:“原來是場噩夢啊……” “哼策肝!你這毒婦竟也來了?” 一聲冷哼從身側(cè)響起隐绵,我...
    開封第一講書人閱讀 37,912評論 0 268
  • 序言:老撾萬榮一對情侶失蹤驳糯,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后氢橙,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體酝枢,經(jīng)...
    沈念sama閱讀 44,355評論 1 303
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 36,666評論 2 327
  • 正文 我和宋清朗相戀三年悍手,在試婚紗的時候發(fā)現(xiàn)自己被綠了帘睦。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點故事閱讀 38,809評論 1 341
  • 序言:一個原本活蹦亂跳的男人離奇死亡坦康,死狀恐怖竣付,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情滞欠,我是刑警寧澤古胆,帶...
    沈念sama閱讀 34,504評論 4 334
  • 正文 年R本政府宣布,位于F島的核電站筛璧,受9級特大地震影響逸绎,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜夭谤,卻給世界環(huán)境...
    茶點故事閱讀 40,150評論 3 317
  • 文/蒙蒙 一棺牧、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧朗儒,春花似錦颊乘、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,882評論 0 21
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至恳不,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間妆够,已是汗流浹背识啦。 一陣腳步聲響...
    開封第一講書人閱讀 32,121評論 1 267
  • 我被黑心中介騙來泰國打工负蚊, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留家妆,地道東北人伤极。 一個月前我還...
    沈念sama閱讀 46,628評論 2 362
  • 正文 我出身青樓,卻偏偏與公主長得像当编,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子臊泌,可洞房花燭夜當晚...
    茶點故事閱讀 43,724評論 2 351

推薦閱讀更多精彩內(nèi)容

  • 8.10 shell特殊符號cut命令8.11 sort_wc_uniq命令8.12 tee_tr_split命令...
    awsome365閱讀 195評論 0 0
  • 第 2 章 SHELL 基礎(chǔ)知識2.1 shell腳本我們在上面簡單介紹了一下什么是shell腳本鲤桥,現(xiàn)在我們來進一...
    LiWei_9e4b閱讀 1,562評論 0 0
  • 字符串 單引號和雙引號的區(qū)別: 單引號 雙引號 拼接字符串 字符串最好放到雙引號中,防止中間有空格等情況渠概。 獲取字...
    零一間閱讀 226評論 0 0
  • 什么是運維 術(shù)語名詞 IDC--(Internet Data Center)互聯(lián)網(wǎng)數(shù)據(jù)中心播揪,主要服務包括整機租用贮喧、...
    lyh165閱讀 2,686評論 0 19
  • Spring Cloud為開發(fā)人員提供了快速構(gòu)建分布式系統(tǒng)中一些常見模式的工具(例如配置管理,服務發(fā)現(xiàn)剪芍,斷路器塞淹,智...
    卡卡羅2017閱讀 134,638評論 18 139