【shell】while read line 與for迴圈的區別

quanshengaa發表於2017-01-06
【背景】
工作過程中遇到要從一個ip列表中獲取ip port,然後ssh ip 到目標機器進行特定的操作,但是編寫指令碼的過程 使用while read line 讀取ip列表,在while迴圈中只讀取第一個ip 後就退出指令碼的情況。
【介紹】
解釋上面遇到的問題之前,先看到for 與while的測試對比,文中ip經過修改。

點選(此處)摺疊或開啟

  1. #/bin/bash
  2. IPS="10.1.1.10 3001
  3. 10.1.1.10 3003
  4. 10.1.1.11 3001
  5. 10.1.1.11 3002
  6. 10.1.1.11 3004
  7. 10.1.1.11 3005
  8. 10.1.1.13 3002
  9. 10.1.1.13 3003
  10. 10.1.1.13 3004
  11. 10.1.1.14 3002"
  12. echo "====while test ===="
  13. i=0

  14. echo $IPS | while read line
  15. do
  16.     echo $(($i+1))
  17.     echo $line
  18. done


  19. echo "====for test ===="
  20. n=0
  21. for ip in $IPS ;
  22. do
  23.    n=$(($n+1))
  24.    echo $ip
  25.    echo $n
  26. done
輸出結果如下:

點選(此處)摺疊或開啟

  1. ====while test ====
  2. 1
  3. 10.1.1.10 3001 10.1.1.10 3003 10.1.1.11 3001 10.1.1.11 3002 10.1.1.11 3004 10.1.1.11 3005 10.1.1.13 3002 10.1.1.13 3003 10.1.1.13 3004 10.1.1.14 3002
  4. ====for test ====
  5. 10.1.1.10
  6. 1
  7. 3001
  8. 2
  9. 10.1.1.10
  10. 3
  11. 3003
  12. 4
  13. 10.1.1.11
  14. 5
  15. 3001
  16. 6
  17. 10.1.1.11
  18. ....
由例子可見 while read line 是一次性將資訊讀入並賦值給line ,而for是每次讀取一個以空格為分割符的字串。
【原因】
while中使用重定向機制,IPS中的所有資訊都被讀入並重定向給了整個while 語句中的line 變數。所以當我們在while迴圈中再一次呼叫read語句,就會讀取到下一條記錄。問題就出在這裡,$line中的最後一行已經讀完,無法獲取下一行記錄,從而退出 while迴圈。

【解決方法】
1 使用ssh -n "command" 
2 ssh "cmd" < /dev/null 將ssh 的輸入重定向輸入。

來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/15797451/viewspace-2131986/,如需轉載,請註明出處,否則將追究法律責任。

相關文章