Bourne Shell:控制語句、條件判斷、文本處理、經常使用命令

    條件判斷是一個程序得到智能的基礎,而Bourne Shell腳本則經過命令 [ 來模擬大多數編程語言中的條件表達式。正則表達式

    shell中支持的控制結構有:shell

(1) if then else fi編程

(2) for in do done數組

(3) while do donebash

    這些關鍵字能夠引導程序檢查狀態碼 $?,從而實現控制。下面講解這個命令如何模擬條件表達式。數據結構

 

文件/目錄判斷
[ -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相似svn

 

數值判斷
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爲真,<=spa

總之,「=」用於比較字符串;「-eq」用於比較整型數命令行

 

複雜邏輯判斷
-a 與
-o 或
! 非

一、若是a>b且a<c
if (( a > b )) && (( a < c ))
if [[ $a > $b ]] && [[ $a < $c ]]
if [ $a -gt $b -a $a -lt $c ]

二、若是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中的括號(), (()), [], [[]]

一、單小括號 ()
①命令組。括號中的命令將會新開一個子shell順序執行,因此括號中的變量不可以被腳本餘下的部分使用。括號中多個命令之間用分號隔開,最後一個命令能夠沒有分號,各命令和括號之間沒必要有空格。
②命令替換。等同於`cmd`,shell掃描一遍命令行,發現了$(cmd)結構,便將$(cmd)中的cmd執行一次,獲得其標準輸出,再將此輸出放到原來命令。注意花括號${}也能夠被看作命令替換,可是二者有所區別,花括號內是定義好的變量,而不是shell命令。
③用於初始化數組。如:array=(a b c d)

二、雙小括號 (( ))
①整數擴展。這種擴展計算是整數型的計算,不支持浮點型。((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 ]。

三、單中括號 []
①標準命令 [ 和 test 是具備相同做用,區別在於 [ 命令的最後一個參數是 "]" 。
②在正則表達式中用於表示字符範圍。做爲test用途的中括號內不能使用正則。
④在一個array 結構的上下文中,中括號用來引用數組中每一個元素的編號。

四、雙中括號[[ ]]
①[[是 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,也就實現了對文本的增(插入)、刪、改(替換)、查

一、find命令用於查找文件,如:

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

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

用於查找磁盤上大於1G的文件。

 

二、grep命令用於查找文本,格式爲:

grep <pattern> <filename>

 

三、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命令會把從管道中得到的輸入拆分,逐個做爲下一個命令的輸入。 

相關文章
相關標籤/搜索