2014-01-28 95 views
1

我改變了第一塊空間 - 劃定數據庫的一段代碼:重定向讀取輸出

if [[ "$(cut -d ' ' -f 1 commandnames.txt | grep -F "$2")" == "" ]] ; then 
    while read -r name rest; do 
    if [[ "$1" == "$name" ]] 
    then echo "$2 $rest" 
    else echo "$name $rest"; fi 
    done <commandnames.txt> commandnames.txt 
    echo "Renamed $1 to $2."    
fi 

然而,> commandnames.txt不工作,而不是清除文件。當輸出到stdout時它工作正常。我試圖把while循環,直到標準輸出重定向到一個子shell,但它似乎沒有工作。任何想法爲什麼它不起作用?

回答

2

當執行

while read -r name rest; do 
... 
done <commandnames.txt> commandnames.txt 

這是發生了什麼:

  1. < commandnames.txt:打開 「commandnames.txt」 閱讀
  2. > commandnames.txt:打開 「commandnames.txt」 寫入和截斷它。
  3. while read -r name rest:一次讀取一行,直至標準輸入是空

因爲步驟2截斷文件,循環運行0次,所以沒有什麼寫。該文件因此是空的。

修復很簡單:避免在讀取之前刪除輸入。

您可以通過編寫到一個臨時文件,然後覆蓋你原來當你做這樣做:

while read -r name rest; do 
... 
done <commandnames.txt> tmpfile && mv tmpfile commandnames.txt 
1

但是,> commandnames.txt不起作用,而是清除 文件。

> outfile截斷 開始與文件。

因此,您嘗試從同一文件讀取將不會產生任何結果。

將輸出重定向到不同的文件,並在需要時將其重定向到mvcp


manual(重點煤礦)報價:

輸出的重定向導致其名稱結果從 膨脹字的要被打開文件描述符寫入文件Ñ或 標準輸出(文件描述符1)如果沒有指定n。如果 文件不存在,則會創建它; 如果確實存在,則將其截斷爲 零大小

+0

它工作時,我輸出到標準輸出;這不是問題。我將編輯原始問題。編輯:好的,我看到你的編輯。截斷髮生在中間命令? – bb010g

+1

@ bb010g是的,它不起作用__因爲你試圖將輸出重定向到__same文件___。 – devnull

1

你不會設法做到這一點沒有某種形式的臨時存儲。

如果你是100%肯定,你的commandnames.txt文件將永遠不會成爲太大,你可以文件讀入到一個變量,然後解析變量

GV_LINES=$(cat test_lines.txt) 
while read LV_LINE 
do 
    echo "${LV_LINE}_suffix" 
done <<< "${GV_LINES}" > test_lines.txt 

別人看的內容mktemp或tempfile命令來創建臨時文件