自己動手寫乙個簡單的Shell之四 流程控制

2021-05-04 06:10:17 字數 1401 閱讀 2124

shell中的流程控制

前面我們實現了shell的兩個主要功能:執行命令和處理命令列。現在我們來簡單實現shell的第三個功能——可程式設計。任何一種程式語言都需要對流程進行控制,shell也不例外,這裡就簡單實現在shell中如何提供if控制語句。shell中的if語句的作用與其他語言的if語句相同:條件檢測。如果條件為正值,則有一部分**被執行。不過這裡有一點與其他語言不同,在shell中,if語句有以下特點:

1、條件是乙個命令,返回正值意味著命令執行成功。

2、exit(0)代表成功。

3、如果if後的條件是一系列的命令,那麼最後乙個命令的exit值被用作這個語句塊的條件值,並由此來決定條件是否成立。

在shell中if的工作流程主要如下:

1、shell執行if之後的命令

2、shell檢查命令的exit狀態

3、exit的狀態為0意味著成功,非0意味著失敗

4、如果成功,shell執行then部分的**

5、如果失敗,shell執行else部分的**

6、關鍵字fi標識if塊的結束

在shell中增加if

現在已經知道if控制語句做什麼,也知道它是如何工作的。那麼如何在shell中增加if語句呢?在前面的版本中,shell的控制流從splitline直接到fork,每個命令都被直接傳給exec。新增if語句後命令處理變得複雜,我們這裡用process函式來處理。

process將指令碼看作乙個接乙個的**區域。第乙個區域是then**塊,第2個區域是else**塊,第3個是在if語句之外的**塊。如下圖所示,

對於不同的區域,shell的處理方法是不同的。

1、if語句之外的區域,稱為中立區。對於這類區域的**,簡單地度一條,分析一條,執行一條。

2、if和then之間的區域。這個區域中,shell每執行一條命令就記錄下它的退出狀態

3、then到fi或else之間的區域。這個區域中,shell如果遇到if語句就重複第2個處理方法。

4、else到fi之間的區域。在fi後又回到中立區。

shell記錄當前區域型別,還必須記錄在wait_then區域中執行命令的結果。不同區域的處理方法不同,特定的區域與程式的特定狀態聯絡在一起。proces通過3個函式來處理區域問題。

is_control_command返回乙個布林變數告訴process這條命令是指令碼語言的一部分還是一條可執行的命令。

do_control_command處理關鍵字if、then和fi,每個關鍵字都是區域的界標。這個函式更新狀態變數並執行必要的操作。

ok_to_execute根據當前的狀態和條件命令的結果返回乙個布林值,說明能否執行當前命令。

下面是程式執行結果和原始碼(這裡把原來乙個檔案分割成了幾個檔案):

自己動手寫乙個單鏈表

單向鍊錶 單鏈表 是鍊錶的一種,其特點是鍊錶的鏈結方向是單向的,對鍊錶的訪問要通過順序讀取從頭部開始。鏈式儲存結構的線性表將採用一組任意的儲存單元存放線性表中的資料元素。由於不需要按順序儲存,鍊錶在插入 刪除資料元素時比順序儲存要快,但是在查詢乙個節點時則要比順序儲存要慢 使用鏈式儲存可以克服順序線...

自己動手寫乙個單鏈表

單向鍊錶 單鏈表 是鍊錶的一種,其特點是鍊錶的鏈結方向是單向的,對鍊錶的訪問要通過順序讀取從頭部開始。鏈式儲存結構的線性表將採用一組任意的儲存單元存放線性表中的資料元素。由於不需要按順序儲存,鍊錶在插入 刪除資料元素時比順序儲存要快,但是在查詢乙個節點時則要比順序儲存要慢 使用鏈式儲存可以克服順序線...

自己動手寫乙個單鏈表

單向鍊錶 單鏈表 是鍊錶的一種,其特點是鍊錶的鏈結方向是單向的,對鍊錶的訪問要通過順序讀取從頭部開始。鏈式儲存結構的線性表將採用一組任意的儲存單元存放線性表中的資料元素。由於不需要按順序儲存,鍊錶在插入 刪除資料元素時比順序儲存要快,但是在查詢乙個節點時則要比順序儲存要慢 使用鏈式儲存可以克服順序線...