文章详情

  • 游戏榜单
  • 软件榜单
关闭导航
热搜榜
热门下载
热门标签
php爱好者> php文档>Shell Script

Shell Script

时间:2007-03-12  来源:darrenshen

http://plum.cs.nccu.edu.tw/~lien/UNIX/SHELL/hardcopy.htm  
Shell Script
前言
Setup
Script的基本結構及觀念
變數
執行命令
流程控制
Expression
Test
前言
        Original material from 台大計算機中心網路推廣協會 網路課程講義

⊙ 批次檔

    在DOS 中,你可能會從事一些例行的重覆性工作,此時你會將這些重覆性的命令寫成批次檔,只要執行這個批次檔就等於執行這些命令。大家會問在Unix中是否有批次處理這個東東,答案是有的。在Unix中不只有如DOS 的批次處理,它的功能比起DOS 更強大,相對地也較複雜,已經和一般的高階語言不相上下。在Unix中大家都不叫做批次檔,而叫做Shell Script。

⊙ Shell scripts are ASCII file

    一般而言,Shell Script的地位和其它的可執行檔(或命令)是完全相同的,只不過Shell Script是以文字檔的方式儲存,而非二進位檔。
    而執行Shell Script時,必須有一個程式將其內容轉成一道道的命令執行,而這個程式其實就是Shell ,這也就是為什麼我們叫做Shell Script的原因(往後我們稱為Script)。
    不同Shell 的Script基本上會有一些差異,所以我們不能將寫給A shell 的Script用B shell 執行。而在Unix中大家最常使用Bourne Shell, Korn Shell 以及C Shell.
國立政治大學資訊科學系 連耀南 [email protected]  intro.htm, 
Setup
將文字檔設為可執行的Shell Script
    如果我們已經寫好Script,如何將其設成可執行檔呢?因為Script其實是一個可執行檔,所以必須將其存取權設定成可執行。我們可以使用下列命令更改存取權:
chmod u+x filename 只有自己可以執行,其它人不能執行
chmod ug+x filename 只有自己以及同一群可以執行,其它人不能執行
chmod +x filename 所有人都可以執行

⊙ 指定使用Shell

    而我們如何指定使用那一個Shell 來解釋所寫的Script呢?幾種基本的指定方式如下所述:
      1. 如果Script的第一個非空白字元不是"#",則它會使用Bourne Shell。
      2. 如果Script的第一個非空白字元是"#"時,但不以"#!"開頭時,則它會使用C Shell。
      3. 如果Script以"#!"開頭,則"#!"後面所寫的就是所使用的Shell,而且要將整個路徑名稱指出來。
    這裡建議使用第三種方式指定Shell ,以確保所執行的就是所要的。
      Bourne Shell的路徑名稱為/bin/sh ,
      而C Shell 則為/bin/csh。

─ 使用Bourne Shell

 #!/bin/sh 

─ 使用C Shell

 # C Shell Script 
    or
 #!/bin/csh 

─ 使用/etc/perl

 #! /etc/perl 
    除了在Script內指定所使用的Shell 外,你也可以在命令列中強制指定。
      用C Shell 執行某個Script
 csh filename 
      用Bourne Shell 執行某個Script
 sh filename 
      此時的Script的存取權就不一定要為可執行檔,其內部所指定的Shell 也會無效
國立政治大學資訊科學系 連耀南 [email protected]  setup.htm, 
Script的基本結構及觀念
    Script是以行為單位,我們所寫的Script會被分解成一行一行來執行。而每一行可以是命令、註解、或是流程控制指令等。如果某一行尚未完成,可以在行末加上"\" ,這個時候下一行的內容就會接到這一行的後面,成為同一行,如下
 echo The message is \ too long so we have \ to split it into \ several lines 
    當Script中出現"#" 時,再它後面的同一行文字即為註解,Shell 不會對其翻譯。
    在Script中要執行一個命令的方法和在命令列中一樣,你可以前景或背景執行,執行命令時也會需要設定一些環境變數。
    Script的流程控制和一般高階語言的流程控制沒有什麼兩樣,也和高階語言一樣有副程式。這些使得Script的功能更加強大。
    為了達到與高階語言相同的效果,我們也可以在Script中設定變數,如此使Script 成為一個名付其實的高階語言。
國立政治大學資訊科學系 連耀南 [email protected]  concept.htm, 
變數
    Bourne Shell的變數型態只有字串變數,所以要使用數值運算則必須靠外部命令達 成目的。而其變數種類有下列幾種:
使用者變數 系統變數(環境變數) 唯讀的使用者變數 特殊變數

⊙ 使用者變數

    這是最常使用的變數,我們可以任何不包含空白字元的字串來當做變數名稱。
      設定變數值時則用下列方式:
 var=string 
      取用變數時則在變數名稱前加上一"$" 號。
 name=Tom echo name echo $name 
    結果如下:
 name Tom 

⊙ 系統變數(環境變數)

─ 和使用者變數相似,只不過此種變數會將其值傳給其所執行的命令。

    將一使用者變數設定為系統變數
 export var 
 name=Tom export name 
    以下是使用者一進入系統之後就已設定好的系統變數:
$HOME 使用者自己的目錄
$PATH 執行命令時所搜尋的目錄
$TZ 時區
$MAILCHECK 每隔多少秒檢查是否有新的信件
$PS1 在命令列時的提示號
$PS2 當命令尚未打完時,Shell 要求再輸入時的提示號
$MANPATH man 指令的搜尋路徑

⊙ 唯讀的使用者變數

─ 和使用者變數相似,只不過這些變數不能被改變。

    將使用者變數設成唯讀的,只要加上:
 readonly var 
      而若只打readonly則會列出所有唯讀的變數。還有一點,系統變數不可以設定成唯讀的。
 name=Tom readonly name echo $name name=John readonly 
    結果如下:
 Tom name: is read only readonly name readonly ...... 

⊙ 特殊變數

    有些變數是一開始執行Script時就會設定,並且不以加以修改,但我們不叫它 唯讀的系統變數,而叫它特殊變數(有些書會叫它唯讀的系統變數),因為這 些變數是一執行程式時就有了,況且使用者無法將一般的系統變數設定成唯讀 的。
$0 這個程式的執行名字
$n 這個程式的第n個參數值,n=1..9
$* 這個程式的所有參數
$# 這個程式的參數個數
$$ 這個程式的PID
$! 執行上一個背景指令的PID
$? 執行上一個指令的返回值

─ Shift

    當你執行這個程式時的參數數目超過9 個時,我們可以使用shift 命令將參數 往前移一格,如此即可使用第10個以後的參數。
    除此之外,可以用set 命令改變$n及$*,方法如下:
 set string 
    如此$*的值即為string,而分解後則會放入$n。如果set 命令後面沒有參數, 則會列出所有已經設定的變數以及其值。

─ Example

    檔名:ex1 參數:this is a test
 echo Filename: $0 echo Arguments: $* echo No. of args.: $# echo 2nd arg.: $2 shift echo No. of args.: $# echo 2nd arg.: $2 set hello, everyone echo Arguments: $* echo 2nd arg.: $2 
    結果如下:
 Filename: ex1 Arguments: this is a test No. of args.: 4 2nd arg.: is No. of args.: 3 2nd arg.: a Arguments: hello, everyone 2nd arg.: everyone 
    值得一提的是,當你想從鍵盤輸入一變數值時,你可以使用下面的命令:
 read var1 var2..... 
    這時read會將一個字分給一個變數。如果輸入的字比變數還多,最後一個變數會將 剩下的字當成其值。如果輸入的字比變數還少,則後面的變數會設成空字串。
    如果需要處理數值運算,我們可以使用expr命令。
國立政治大學資訊科學系 連耀南 [email protected]  variable.htm, 
執行命令
    在Bourne Shell中有五種方法執行一個命令,而這五種方式所產生的果有些許的不同。
1. 直接下命令
2. 使用sh命令
3. 使用"."命令
4. 使用exec命令
5. 使用命令替換

⊙ 直接下命令

    這個方式和在命令列中直接下命令的效果一樣。

⊙ 使用sh命令

 sh command 
    這個檔案必須是Bourne Shell的Script,但這個檔案並不一定要設成可執行。 除此之外和直接下命令的方式一樣。

⊙ 使用"."命令

 
  • command
  •  
      這時和使用sh命令相似,只不過它不像sh一般會產生新的process ,相反地,它會在原有的process 下完成工作。

    ⊙ 使用exec命令

     exec command 
      此時這個Script將會被所執行的命令所取代。當這個命令執行完畢之後,這個 Script也會隨之結束。

    ⊙ 使用命令替換 (like function call)

      這是一個相當有用的方法。如果想要使某個命令的輸出成為另一個命令的參數 時,就一定要使用這個方法。我們將命令列於兩個"`" 號之間,而Shell 會以 這個命令執行後的輸出結果代替這個命令以及兩個"`" 符號。

    ─ Example

     str='Current directory is '`pwd` echo $str 
      結果如下:
     Current directory is /users/cc/mgtsai 
        這個意思是pwd 這個命令輸出"/users/cc/mgtsai",而後整個字串代替原 來的`pwd` 設定str 變數,所以str 變數的內容則會有pwd 命令的輸出。

    ─ Example

     number=`expr $number + 1` 
        這就是先前所提要作數值運算的方法,基本上expr命令只將運算式解,而 後輸出到標準輸出上。如果要將某變數設定成其值,非得靠命令替換的方 式不可。這個例子是將number變數的值加1 後再存回number變數。
    國立政治大學資訊科學系 連耀南 [email protected]  execute.htm, 
    流程控制

    ─ Target of Condition Test

      The status of an execution (true or false)
      "test" command is very very useful
     test $# = 0 
        如果執行這個程式沒有參數時,會傳回非零值代表"$# = 0"這個條件成立。反 之則會傳回零。

    ⊙ if then

    ─ 語法以及流程圖如下

     if [ condition ] then then-commands fi 
        condition 是一個test命令。

    ─ Example

      檔名:chkarg
     if [ $# != 0 ] then echo Arg1: $1 fi 
     $ chkarg Hello Arg1: Hello $ chkarg $ 
      Alternatives
     if test $# != 0 then echo Arg1: $1 fi 
     if [ $# != 0 ] then echo Arg1: $1 fi 
     [ $# != 0 ] && echo Arg1: $1 

    ⊙ if then else

      語法以及流程圖如下
     if [ condition ] then then-commands else else-commands fi 

    ⊙ if then elif

      語法以及流程圖如下
     if [ condition1 ] then commands1 elif [ condition2 ] then commands2 else commands3 commands3 fi 

    ─ Example

     echo 'word 1: \c' read word1 echo 'word 2: \c' read word2 echo 'word 3: \c' read word3 if [ "$word1" = "$word2" -a "$word2" = "$word3" ] then echo 'Match: words 1, 2, & 3' elif [ "$word1" = "$word2" ] then echo 'Match: words 1 & 2' elif [ "$word1" = "$word3" ] then echo 'Match: words 1 & 3' elif [ "$word2" = "$word3" ] then echo 'Match: words 2 & 3' else echo 'No match' fi 

    ⊙ for in

      語法以及流程圖如下
     for var in arg-list do commands done 

    ─ Example

     for a in xx yy zz do echo $a done 
      結果如下:
     xx yy zz 

    ⊙ for

      語法以及流程圖如下
     for var do commands done 

    ─ Example

     檔名:lstarg for a do echo $a done 
     $lstarg xx yy zz xx yy zz 

    ⊙ while

      語法以及流程圖如下
     while [ condition ] do commands done 

    ─ Example

     number=0 while [ $number -lt 10 ] do echo "$number\c" number=`expr $number + 1` done echo 
      結果如下:
     0123456789 

    ⊙ until

      語法以及流程圖如下
     until [ condition ] do commands done 
      它和while 的不同只在於while 是在條件為真時執行迴圈,而until 是在條件 為假時執行迴圈。

    ⊙ break及continue

      這兩者是用於for, while, until 等迴圈控制下。break 會跳至done後方執行 ,而continue會跳至done執行,繼續執行迴圈。

    ⊙ case

      語法以及流程圖如下
     case str in pat1) commands1;; pat2) commands2;; pat3) commands3;; esac 
      而pat 除了可以指定一些確定的字串,也可以指定字串的集合,如下
    * 任意字串
    ? 任意字元
    [abc] a, b, 或c三字元其中之一
    [a-n] 從a到n的任一字元
      | 多重選擇

    ─ Example

     echo 'Enter A, B, or C: \c' read letter case $letter in A|a) echo 'You entered A.';; B|b) echo 'You entered B.';; C|c) echo 'You entered C.';; *) echo 'Not A, B, or C';; esac 

    ⊙ 函數

      格式如下
     function-name() { commands } 
      而要呼叫此函數,就像在命令列下直接下命令一般。
    國立政治大學資訊科學系 連耀南 [email protected]  flow.htm, 
    Expression

    ─ 格式

     expr expression 
      expression是由字串以及運算子所組成,每個字串或是運算子之間必須用空白隔開 。下表是運算子的種類及功能,而優先順序則以先後次序排列,我們可以利用小括 號來改變運算的優先次序。其運算結果則輸出至標準輸出上。
    : 字串比較。比較的方式是以兩字串的第一個字母開始,而以第二個字串的 字母結束。如果相同時,則輸出第二個字串的字母個數,如果不同時則傳 回0 。
    * 乘法
    / 除法
    % 取餘數
    + 加法
    - 減法
    < 小於
    <= 小於等於
    = 等於
    != 不等於
    >= 大於等於
    > 大於
    & AND運算
    | OR運算
        當expression中含有"*", "(", ")" 等符號時,必須在其前面加上"\" ,以免被 Shell 解釋成其它意義。

    ─ Example

     expr 2 \* \( 3 + 4 \) 
        其輸出為 14
    國立政治大學資訊科學系 連耀南 [email protected]  expr.htm, 
    Test
      命令格式
     test expression 
      expression中包含一個以上的判斷準則以作為test評詁的標準。兩準則間用"-a"代 表邏輯AND 運算,\\\"-o"代表邏輯OR運算,而在準則前放置一"!" 代表NOT 運算。如 果沒有括號,則優先權則為"!" > "-a" > "-o" 。和expr命令相同,相使用左右括 號時,必須在其前面加上"\" 。以下是有關準則的敘述(合敘述時傳回真,否則傳 回偽):
    string string不為空白字串
    -n string string的長度大於0
    -z string string的長度等於0
    string1=string2 string1等於string2
    string1!=string2 string1不等於string2
    int1 -gt int2 int1大於int2
    int1 -ge int2 int1大於等於int2
    int1 -eq int2 int1等於int2
    int1 -ne int2 int1不等於int2
    int1 -le int2 int1小於等於int2
    int1 -lt int2 int1小於int2
    -r filename 檔案可讀取
    -w filename 檔案可寫入
    -x filename 檔案可執行
    -f filename 檔案為一般檔
    -d filename 檔案為目錄
    -s filename 檔案為非空的一般檔

    ─ Example

     test -r "$filename" -a -s "$filename" 
    國立政治大學資訊科學系 連耀南 [email protected]  testing.htm, 
    相关阅读 更多 +
    排行榜 更多 +
    辰域智控app

    辰域智控app

    系统工具 下载
    网医联盟app

    网医联盟app

    运动健身 下载
    汇丰汇选App

    汇丰汇选App

    金融理财 下载