2012-03-13 55 views
5

我有一個bash文件,提示用戶輸入一些參數,如果沒有提供任何參數,則使用默認值。然後腳本繼續執行一些其他帶參數的命令。 這很好 - 直到最近的加入沒有問題。如何在while循環讀取行中讀取用戶?

在嘗試從txt文件中讀取NAMES參數時,我添加了一個while循環來獲取文件中的名稱,但我仍然希望提示其餘的參數。

但是,一旦我添加了while循環,輸出將顯示get_ans()中的打印提示,並且從不會暫停讀取,因此將選擇所有默認值。

我想從文件中讀取第一個參數,然後從提示用戶讀取所有後續文件。

我通過添加while循環而破壞了什麼?

cat list.txt | 
while read line 
do 
    get_ans "Name" "$line" 
    read NAME < $tmp_file 

    get_ans "Name" "$line" 
    read NAME < $tmp_file 
done 

function get_ans 
{ 
    if [ -f $tmp_file ]; then 
    rm $tmp_file 

    PROMPT=$1 
    DEFAULT=$2 

    echo -n "$PROMPT [$DEFAULT]: " 
    read ans 
    if [ -z "$ans" ]; then 
    ans="$DEFAULT" 
    fi 
    echo "$ans" > $tmp_file 
} 

+0

我想看看你的其他答案這(一個告訴你如何做決定接受前_solve_的問題,它不只是什麼)。 – 2012-03-13 17:05:12

回答

3

您將數據傳輸到您的while循環STDIN中。所以readget_ans也從該STDIN流中獲取數據。

可以通過管道將數據導入,同時在不同的文件描述符,以避免這個問題,並停止與臨時文件煩心事:

while read -u 9 line; do 
    NAME=$(get_ans Name "$line") 
done 9< list.txt 

get_ans() { 
    local PROMPT=$1 DEFAULT=$2 ans 
    read -p "$PROMPT [$DEFAULT]: " ans 
    echo "${ans:-$DEFAULT}" 
} 
+0

讀了<&9 – 2012-03-13 17:24:19

1

(注碼不會複製&糊所以請原諒錯別字實際的代碼之前已經在main()定義的函數)當你管一個命令到另一個命令行,像:

$ foo | bar 

殼會使得bar的標準輸入來自foo的標準輸出進行設置。 foo發送到標準輸出的任何內容將直接轉到bar的標準輸入。

就你而言,這意味着你的腳本可以讀取的唯一東西是cat命令的標準輸出,它將包含文件的內容。

而不是在命令行中使用管道,使文件名是您的腳本的第一個參數。然後打開並讀取代碼中的文件,並像平常一樣從用戶那裏讀取。

+0

好吧,這很有道理。謝謝 – 2012-03-13 17:01:45

+0

好的,刪除管道並在讀取線路時使用;做...完成<$ 1,它仍在跳過輸入讀取。 – 2012-03-13 17:11:12

3

要直接從終端讀取,而不是從標準輸入(假設你是在* NIX機器,而不是一臺Windows計算機):

while read foo</some/file; do 
    read bar</dev/tty 
    echo "got <$bar>" 
done