Read
while read -r line || 是什麼意思?[-n$l我ne[−n$l一世n和[ -n $line]
是什麼意思?
不久前,我發現了一些用於從文件中讀取輸入的程式碼,我相信來自 Stack Exchange,我能夠適應我的需求:
while read -r line || [[ -n "$line" ]]; do if [[ $line != "" ]] then ((x++)); echo "$x: $line" <then do something with $line> fi done < "$1"
我現在正在審查我的腳本並試圖了解它在做什麼……我不明白這個語句在做什麼:
while read -r line || [[ -n "$line" ]];
我知道 -r 選項表示我們正在將原始文本讀入一行,但我
|| [[ -n "$line" ]]
對語句的部分感到困惑。有人可以解釋一下這是在做什麼嗎?
[[ -n "$line" ]]
測試$line
(剛剛讀取的變數read
)是否不為空。它很有用,因為read
當且僅當它在文件結尾之前看到換行符時才返回成功。如果輸入包含最後沒有換行符的行片段,則此測試將擷取它,並且循環也將處理最後的不完整行。如果沒有額外的測試,這樣一個不完整的行將被讀入$line
,但被循環忽略。我說的是“不完整的行”,因為文本文件和行的 POSIX 定義需要在每行末尾有一個換行符。其他工具
read
也可以關心,例如wc -l
計算換行符,因此忽略最後的不完整行。參見例如在文件末尾添加新行有什麼意義?以及為什麼文本文件應該以換行符結尾?就這樣。該
cmd1 || cmd2
結構當然與 C 中的等價物一樣。如果第一個命令返回錯誤狀態,則第二個命令執行,結果是執行的最後一個命令的退出狀態。比較:
$ printf 'foo\nbar' | ( while read line; do echo "in loop: $line"; done; echo "finally: $line" ) in loop: foo finally: bar
和
$ printf 'foo\nbar' | ( while read line || [[ -n $line ]]; do echo "in loop: $line"; done; echo "finally: $line" ) in loop: foo in loop: bar finally: