1. 程式人生 > 實用技巧 >Unix Shell指令碼程式設計知識點總結及範例

Unix Shell指令碼程式設計知識點總結及範例

指令碼程式語言與編譯型語言:

  1. 指令碼程式語言:(Bash)

  2. 指令碼程式語言通常是解釋型(interpreted),主要由直譯器(interpreter)讀入程式程式碼,並將其轉換成內部的形式加以執行。

  3. 優點:

  4. 能夠輕易處理檔案與目錄之類的物件。

  5. 缺點:

  6. 執行效率通常不如編譯型語言

  7. 編譯型語言:(C、C++、Java、Fortran、Ada、Pascal)

  8. 編譯型語言多半運作於底層,所處理的是位元組、整數、浮點數或其它及其機器層經的物件。

SHELL指令碼的基本語法格式:

  1. 指令碼必須以#!開頭:(# cat /etc/shells)

  2. 例如#!/bin/bash(直譯器)

  3. # 其中間可以新增一些註釋資訊,例如指令碼的使用方法、指令碼的功能、建立日期、作者等相關資訊

  4. 然後賦予指令碼具有執行許可權,# chmod +x scripts.sh

  5. 執行則使用./scripts.sh ##也可以將此指令碼的路徑新增到PATH變數中,以後直接使用指令碼名稱直接執行。

  6. 指令碼的測試工具bash:

  7. -n:檢查指令碼是否有語法錯誤,有則顯示錯誤資訊,否則無資訊(沒有訊息才是最好的訊息)

  8. -x:檢查指令碼在執行中的詳細過程(排錯時,經常會用到)

  9. exit:退出指令碼(其數值為0-255)

  10. 如果指令碼沒有明確定義退出碼,那麼在執行指令碼結束前的退出碼為此指令碼的退出碼。

  11. # echo $? ##檢視上一個命令執行結果所顯示的狀態碼

SHELL指令碼的邏輯關係總結:

  1. 邏輯與:符號為&&:

  2. 如果其中一個為假,則結果一定為假

  3. 如果第一個條件結果為假,則第二個條件不用再判斷,最終結果已顯示

  4. 如果第一個條件結果為真,則第二個條件必須判斷

  5. 範例:

  6. # useradd redhat && echo "redhat" | passwd --stdin redhat
    解說:如果useradd redhat執行成功,則繼續執行下一條命令,否則終止。

  1. 邏輯或||:

  2. 如果其中一個條件結果為真,則結果一定為真,不用檢查後面的語句

  3. 如果其中一個條件結果為假,則檢查下一個條件語句

  4. 範例:

  5. # id redhat || useradd redhat

  6. 解說:如果redhat使用者存在,就顯示redhat使用者相關資訊,否則新增此賬戶。

  7. 邏輯與和邏輯或聯合使用範例:

  8. # id redhat && echo “redhat already existing“ || useradd redhat

  9. 解說:如果redhat使用者存在,則顯示redhat使用者已存在,否則新增此賬戶。

條件判斷語句總結:

  1. 單分支if語句雙分支if語句 多分支if語句case選擇語句

  2. if 判斷條件 ;then if 判斷條件;then if 判斷條件;thencase $1 in

  3. statement statement statement string)

  4. ...... ........ ......... statement;;

  5. fi else elif 判斷條件;then string2)

  6. statement statement statement;;

  7. ..... ......... ......)

  8. fi elif 判斷條件;then statement;;

  9. statement esac

  10. .........

  11. else

  12. statement

  13. fi

範例:

200627947.png

  1. 指令碼分析:

  2. 主要功能:傳遞一個不同的引數,來完成使用者的建立、新增密碼、刪除使用者。

  3. 詳細說明:

  4. 當我們傳遞--add引數給此指令碼時,此指令碼為完成指定使用者的新增,如果新增的使用者存在,則提示使用者以存在,否則新增指定使用者並建立以使用者為自身的密碼;

  5. 當我們傳遞--del引數給此指令碼時,此指令碼會刪除我們指定的使用者,如果存在則刪除此使用者,否則提示使用者不存在。

  6. 當我們傳遞--help引數給此指令碼時,此指令碼會給我們現實指令碼的使用方法。

  7. 當我們傳遞其它引數時,會提示無法識別的選項。


POSIX的結束狀態總結:

  1. 0: ##命令成功所顯示的狀態

  2. >0: ##在重定向或單詞展開期間(~、變數、命令、算術展開及單詞切割)失敗

  3. 1-125 ##命令不成功所顯示的狀態。

  4. 126 ##命令找到了,但檔案無法執行所顯示的狀態

  5. 127 ##命令找不到,所顯示的狀態

  6. >128 ##命令因收到訊號而死亡

替換運算子總結(變數的賦值):

  1. ${varname:-word}

  2. 如果varname存在且非null,則返回其值;否則,返回word;

  3. 用途:如果變數未定義,則返回預設值

  4. 範例:如果count未定義,則${count:-0}的值為0

  5. ${varname:=word}

  6. 如果varname存在且非null,則返回其值;否則,將varname設定為word,並返回其值;

  7. 用途:如果變數未定義,則設定變數為預設值

  8. 範烈:如果count未定義,則${count:=0}的值為0

  9. ${varname:+word}

  10. 如果varname存在且非null,則返回word;否則,返回null

  11. 用途:為測試變數的存在

  12. 範例:如果count已定義,則${count:+1}的值為1

  13. ${varname:?message}

  14. 如果varname存在且非null,則返回其值;否則顯示varname:message,並退出當前命令或指令碼;

  15. 用途:為了捕捉由於變數未定義所導致的錯誤。

  16. 範例:如果count未定義,${count:?"undefined!"}則顯示count:undefined!

模式匹配運算子總結:

  1. 假設path變數的值為:/etc/sysconfig/network-scripts/ifcfg-eth0.text.bak

  2. ${variable#pattern}:

  3. 如果模式匹配於變數值的開頭處,則刪除匹配的最短部分,並返回剩下的部分;

  4. 範例:echo ${path#/*/}的值為etc/sysconfig/network-scripts/ifcfg-eth0.text.bak

  5. ${variable##pattern}

  6. 如果模式匹配於變數值的開頭處,則刪除匹配的最長部分,並返回剩下的部分;

  7. 範例:echo ${path##/*/}的值為ifcfg-eth0.text.bake

  8. ${variable%pattern}

  9. 如果模式匹配於變數的結尾處,則刪除匹配的最短部分,並返回剩下的部分;

  10. 範例:echo ${path%.*}的值為/etc/sysconfig/network-scripts/ifcfg-eth0.text

  11. ${variable%%pattern}

  12. 如果模式匹配於變數的結尾處,則刪除匹配的最長部分,則返回剩餘部分。

  13. 範例:echo ${path%%.*}的值為/etc/sysconfig/network-scripts/ifcfg-eth0

  14. ${#variable}

  15. 顯示variable變數值的字元長度

Shell指令碼常用的迴圈語句總結:

  1. for迴圈 while迴圈 until迴圈

  2. for 變數 in 列表 ;do while condition(條件);do until condition ;do

  3. command... statements statements

  4. done done done


  5. while迴圈:只要condition滿足條件,while會迴圈

  6. until迴圈:只要condition不滿足條件,until會迴圈

test命令

  1. test命令可以處理shell指令碼中的各類工作,它產生的不是一般輸出,而是可使用退出狀態,test接受各種不同的引數,可控制它要執行哪一種測試

  2. 語法:

  3. test [ expression ]

  4. test [ [expression] ]

  5. 用途:

  6. 為了測試shell腳本里的條件,通過退出狀態返回其結果。

  7. 行為模式:

  8. test用來測試檔案的屬性、比較字串、比較數字

  9. 主要選項與表示式:

  10. string string不是null

  11. -b file file是塊裝置檔案(-b)

  12. -c file file是字元裝置檔案(-c)

  13. -d file file為目錄(-d)

  14. -e file file是否存在

  15. -f file file是一般檔案(-)

  16. -g file file有設定它的setgid位

  17. -h file file是一個符號連結

  18. -r file file是可讀的

  19. -s file file是socket

  20. -w file file是可寫的

  21. -x file file是可執行的,或file是可被查詢的目錄

  22. s1 = s2 s1與s2字串相同

  23. s1 != s2 s1與s2字串不相同

  24. n1 -eq n2 整數n1與n2相等

  25. n1 -ne n2 整數n1與n2不相等

  26. n1 -lt n2 整數n1小於n2

  27. n1 -gt n2 整數n1大於n2

  28. n1 -le n2 整數n1小於或等於n2

  29. n1 -ge n2 整數n1大於或等於n2

  30. -n string string是非null

  31. -z string string為null特殊引數變數

  32. 在bash shell中有些特殊變數,它們會記錄命令列引數的個數。例如$#

  33. 你可以只數一下命令列中輸入了多少個引數,而不同測試每個引數。bash為此提供了一個特殊的變數,就是上面所提到的$#

  34. $#的說明

    1. $#特殊變數含有指令碼執行時就有的命令列引數的個數。你可以在指令碼中任何地方來呼叫這個特殊變數來呼叫$#來計算引數的個數

  35. 範例:

    1. vim Count.sh

      #!/bin/bash

      #Script Name: Count.sh

      # Count Parameters number


      echo There were $# parameters.


      chmod +x Count.sh

      ./Count.sh 1 2 3

      There were 3 parameters.


下面來說下${!#}的作用?

既然$#變數含有引數的總數量,那麼${!#}可以呼叫最後一個引數的變數名稱。

範例:

vim Count-1.sh

#!/bin/bash

#Script Name: Count-1.sh

# Print last parameter

params=$#

echo "The last parameter is "$params"

echo "The last parameter is "${!#}"

:wq


chmod +x Count-1.sh

./Count-1.sh 1 2 3

The last parameter is 3

The last parameter is 3








轉載於:https://blog.51cto.com/guodayong/1188606