shell的i/o語法比較複雜,難以理解,更難以正確使用。shell的輸入輸出語法有兩個難點:重定向和檔案描述符。我以前對shell指令碼輸入/輸出的理解也有錯誤。最近重新整理思路,決定寫一篇文章來總結i/o重定向。
一、先介紹幾個基本概念:
(1)檔案(file):在unix/linux中,檔案型別有七種,這七種型別是:目錄、符號鏈結(指向另乙個檔案)、套接字檔案、塊裝置檔案、字元裝置檔案、命名管道檔案、普通檔案。這意味著,i/o裝置被unix/linux視為「特殊」的檔案,所以對裝置進行輸入輸出等同於讀寫檔案。
(2)檔案描述符(file descriptor ):實際上,shell中的檔案描述符等同於c語言中的檔案結構(參見《the c programming languag》的7.5節),它是乙個包含檔案資訊的結構,這些資訊包括:緩衝區的位置,緩衝區中當前字元的位置,檔案是否到達末尾等。shell指令碼通過檔案描述符來讀寫檔案。乙個shell指令碼有10個檔案描述符。其中,0、1、2是標準輸入、標準輸出和標準錯誤,我們可以任意使用的檔案描述符是3 到9。
(3)重定向(redirect):在shell中,我們可以對命令(命令就是程式或指令碼)的標準輸入、標準輸出和標準錯誤進行重定向,使其指向其他檔案。
(4)重定向的作用域(redirect's scope ):重定向的「作用域」這個概念是我自己提出的,它對理解重定向的作用效果非常重要!我們來看下面這幾個例子:
例1:重定向的「作用域」侷限於乙個命令
#!/bin/bash
echo "hello world" > result.txt
解析:這個重定向的作用域是echo命令,命令結束重定向也就結束了。
例2:重定向的「作用域」侷限於乙個迴圈
#!/bin/bash
while read line
doecho "$line"
done < name.txt
解析:這個重定向的作用域是while迴圈,在迴圈執行期間,標準輸入都被重定向到了當前目錄的的name.txt檔案,即每次read都是從檔案中讀取一行,且read是順序讀取檔案的所有行。
while迴圈結束時,重定向就結束了。
#!/bin/bash
while read line < name.txt
doecho "$line"
done
解析:這個重定向的作用域是read命令,每次read都重新進行一次重定向。這造成了可怕的結果,每次都讀取檔案中的第一行,無限迴圈下去。
例3:重定向的「作用域」侷限於整個指令碼
#!/bin/bash
#this script called ltx_test
while read line
doecho "$line"
done
在終端執行這個指令碼,執行命令
ltx_test < name.txt
解析:這個重定向的作用域是整個指令碼,在指令碼執行期間,標準輸入都被重定向到了當前目錄的的name.txt檔案,即每次read都是從檔案中讀取一行,且read是順序讀取每一行。指令碼結束時,重定向就結束了。
二、下面開始討論shell指令碼中輸入/輸出的的兩種情況:
(1)指令碼只使用標準輸入、標準輸出和標準錯誤
shell會自動為我們開啟和關閉0、1、2這三個檔案描述符,我們不需要顯式地開啟或關閉它們。標準輸入是命令的輸入,預設指向鍵盤;標準輸出是命令的輸出,預設指向螢幕;標準錯誤是命令錯誤資訊的輸出,預設指向螢幕。
如果沒有顯式地進行重定向,命令通過檔案描述符0從螢幕讀取輸入,通過檔案描述符1和2將輸出和錯誤資訊輸出到螢幕。但如果我們想從其他檔案(再次強調,i/o裝置在unix/linux中也是檔案)讀取輸入或產生輸出,就需要對0、1、2使用重定向了。其語法如下:
command < filename 把標準輸入重定向到filename檔案中
command 0< filename 把標準輸入重定向到filename檔案中
command > filename 把標準輸出重定向到filename檔案中(覆蓋)
command 1> fielname 把標準輸出重定向到filename檔案中(覆蓋)
command >> filename 把標準輸出重定向到filename檔案中(追加)
command 1>> filename 把標準輸出重定向到filename檔案中(追加)
command 2> filename 把標準錯誤重定向到filename檔案中(覆蓋)
command 2>> filename 把標準輸出重定向到filename檔案中(追加)
command > filename 2>&1 把標準輸出和標準錯誤一起重定向到filename檔案中(覆蓋)
command >> filename 2>&1 把標準輸出和標準錯誤一起重定向到filename檔案中(追加)
command < filename >filename2 把標準輸入重定向到filename檔案中,把標準輸出重定向
到filename2檔案中
command 0< filename 1> filename2 把標準輸入重定向到filename檔案中,把標準輸出重定向
UNIX linux中的引號
unix中的引號分為三種 單引號,雙引號,反引號 單引號 用單引號括起來的字元作為普通字元,即使是特殊字元也不例外.雙引號 除了 和 這幾個字元仍是特殊字元保持其特殊效能以外,其他的字元全部作為普通字元.其中 是用其後指定的變數的值代替此變數和 是轉移字元,指出對其後的字元不做特殊處理.反引號 反引...
Unix Linux中Cron的用法
cron是unix或者linux下用來定時任務的命令,大致的用法如下 1 服務的啟動和關閉 sbin service crond start 啟動服務 sbin service crond stop 關閉服務 sbin service crond restart 重啟服務 sbin service ...
Unix Linux中的 dev fd機制
比較新的unix linux系統都提供名為 dev fd的目錄,其中有檔案0 1 2等檔案,開啟這些檔案,相當於複製這些檔案描述符 例如 fd open dev fd 0 mode 等價於fd dup 0 檔案描述符fd和0將共享乙個檔案表記錄項。我們再來做一些試驗 在debian下執行以下命令 c...