一、shell簡介
shell的作用是解釋執行使用者的指令,使用者輸入一條指令,shell就解釋一行【互動式】。另一種執行指令的方式是【批處理】,使用者事先寫一個shell腳本,其中有很多條指令,shell一次把這些指令執行完。shell程式從腳本中一行一行讀取并執行這些指令,相當于一個使用者把腳本中的指令一行一行敲到shell提示符下執行。shell腳本是解釋執行的,不需要編譯。
1、什麼是shell執行腳本
腳本的字尾一般為.sh
腳本一般由#!開頭,稱作“shebang”,後面跟的是解釋器
腳本注釋時為 # 開頭
執行時需要更改權限:chmod +x
*其實腳本就是一個檔案,可以執行多行指令的檔案。
<a href="https://s3.51cto.com/wyfs02/M02/A7/43/wKioL1nkWq_x75M8AAB88KHqGsA882.png" target="_blank"></a>
shell腳本的第一行千萬不要寫錯:#!/bin/bash.
2、shell腳本的執行過程
shell會fork一個子程序并調用exec執行./test.sh這個程式,exec系統調用把子程序的代碼替換成shell腳本程式的代碼段,并從它的_start開始執行。但是這個腳本.sh檔案是個腳本檔案,根本沒有代碼段和_start函數。是以exec會執行另一種機制。
由于第一行用shebang指定了解釋器,則用解釋器程式代碼替換目前程序,并且從解釋器的_start開始,這個文本檔案被當做指令行參數傳給解釋器。
*解釋型語言隻需要解釋器解釋,不需要編譯器,如shell腳本語言;C語言是編譯型語言
二、shell變量
1、環境變量
環境變量可以從父程序傳給子程序,是以shell程序的環境變量可以從目前的shell程序傳給fork出來的子程序,用printenv可以顯示目前shell程序的環境變量。
*fork函數得到的子程序從父程序繼承了整個程序的位址空間,包括:程序上下文、程序堆棧、記憶體資訊、打開的檔案描述符、信号控制設定、程序優先級、程序組号、目前工作目錄、根目錄。資源限制、控制終端、環境變量等。但是父程序設定的鎖子程序不繼承且子程序的未決信号集被設定為空集。
2、本地變量
隻存在目前shell程序,用set指令可以顯示目前shell程序中定義的所有變量,包括本地和環境變量。
當定義環境變量時,等号的兩邊不能有空格,否則會被shell解釋為指令和指令行參數。一個變量定義後進存在目前shell程序,是本地變量,用export可以把本地變量導出為環境變量。
用unset可以删除已定義的環境變量
VARNAME=value #定義本地變量
export VARNAME=value #導出本地變量,也可以寫為VARNAME=value;
export VARNAME
unset VARNAME #删除已定義的環境變量或本地變量
3、變量引用
如果一個變量叫做VARNAME,用${VARNAME}可以表示它的值,在不引起歧義的情況下也
可以 用$VARNAME表示它的值。通過以下例子比較這兩種表示法的不同:
echo $SHELL
echo $SHELLabc
對比:
echo ${SHELL}
echo ${SHELL}abc
注意,在定義變量時不用$,取變量值時要用$。和C語言不同的是,Shell變量不需要明确定義類型,事實上Shell變量的值都是字元串,比如我們定義VAR=45,其實VAR的值是字元串45而非整數。Shell變量不需要先定義後使用,如果對一個沒有定義的變量取值,則值為空字元串。
三、替換
1、檔案名代換
這些用于比對的字元稱為通配符(Wildcard),具體如下:
通配符 * : 比對0個或多個任意字元
? : 比對一個任意字元
[若幹字元] : 比對方括号中任意一個字元的一次出現
$ ls /dev/ttyS*
$ ls ch0?.doc
$ ls ch0[0-2].doc
$ ls ch[012][0-9].doc
注意,Globbing所比對的檔案名是由Shell展開的,也就是說在參數還沒傳給程式之前已經展開了, 比如上述ls ch0[012].doc指令,如果目前目錄下有ch00.doc和ch02.doc,則傳給ls指令的參數實際上是這兩個檔案名,而不是一個比對字元串。
2.指令行代換
由反引号括起來的也是一條指令,Shell先執行該指令,然後将輸出結果立刻代換到目前指令行中。
$ DATE=`date`
$ echo $DATE
例如定義一個變量存放date指令的輸出:
指令代換也可以用$()表示: $ DATE=$(date)
算術代換:$(())
用于算術計算,$(())中的Shell變量取值将轉換成整數,例如:
$ VAR=45
$ echo $(($VAR+3))
$(())中隻能用+-*/和()運算符,并且隻能做整數運算。
四、轉義字元\
\反斜杠被用作轉義字元,用于去除緊跟其後的單個字元的特殊意義。
例:
touch $ $ #建立一個名為 $的檔案
touch \$\ \$ #建立一個名為 $ $的檔案(中間有空格)
還有一個字元雖然不具有特殊含義,但是要用它做檔案名也很麻煩,就是-号。如果要建立一個檔案名以-号開頭的檔案,這樣是不行的: 即使加上\轉義也還是報錯: 因為各種UNIX指令都把-号開頭的指令行參數當作指令的選項,而不會當作檔案名。如果非要處理 以-号開頭的檔案名,可以有兩種辦法:
touch ./-hello #前面加上目前路徑
touch -- -file #前面加上兩個--
五、單引号和雙引号
1、單引号
和C語言不一樣,Shell腳本中的單引号和雙引号一樣都是字元串的界定符,而不是字元的界定符。單引号用于保持引号内所有字元的字面值,即使引号内的\和回車也不例外, 但是字元串中不能出現單引号。如果引号沒有配對就輸入回車,Shell會給出續行提示符,要求使用者把引号配上對。
2、雙引号
雙引号用于保持引号内所有字元的字面值(回車也不例外),但以下情況除外:
$加變量名可以取變量的值
反引号仍表示指令替換
\$表示$的字面值
\`表示`的字面值
\"表示"的字面值
\\表示\的字面值 除以上情況之外,在其它字元前面的\無特殊含義,隻表示字面值
<a href="https://s5.51cto.com/wyfs02/M01/08/99/wKiom1nkfNbBdkNgAAAtJPw0Jlc200.png" target="_blank"></a>
<a href="https://s5.51cto.com/wyfs02/M02/08/99/wKiom1nkfNaQeKNdAAAksYdiFbE960.png" target="_blank"></a>
本文轉自 8yi少女的夢 51CTO部落格,原文連結:http://blog.51cto.com/zhaoxiaohu/1972926,如需轉載請自行聯系原作者