2012-09-19 44 views
1

如此遠熟練製作的腳本如何使用awk挑出「第二」值?

iostat -p -x 1 2| grep $1[^[:digit:]] | awk '{print $9}' 

將返回兩行:

0.16 
0.00 

因爲iostat的走的是兩條樣品。但你已經知道了。我的問題是,既然你和我都知道每次都會有兩行,我怎麼挑出第二個呢?

+0

什麼跟讀者奉承的?直截了當的問題通常更易於閱讀。 – nneonneo

回答

6

{print $9}之前添加NR==2告訴awk到2

例如,賽會記錄我的系統上,

$ iostat -x /dev/sda 1 2 | grep sda 

$ iostat -x /dev/sda 1 2 | grep sda | awk 'NR==1 {print $9}' 

$ iostat -x /dev/sda 1 2 | grep sda | awk 'NR==2 {print $9}' 

生產

sda    0.11  1.04 2.00 1.28 125.95 63.24 115.15  0.07 21.04 4.66 46.60 2.36 0.78 
sda    0.00  0.00 0.00 0.00  0.00  0.00  0.00  0.00 0.00 0.00 0.00 0.00 0.00 
0.07 
0.00 

這裏是 「0.00」 線是第三個命令的結果。

附加說明:不需要單獨運行grep命令,因爲awk可以匹配文本。但是,awk腳本則需要一個索引變量。下面的第一個例子是一個簡單的grep來顯示awk的工作原理。接下來的兩個例子是直接的awk代碼,它有一個匹配測試來增加一個索引,另一個匹配測試加上索引測試來打印。最後一個例子展示瞭如何擺脫匹配表達式的額外外觀。請注意,在這些示例中,爲了清晰起見,我將print $9替換爲print,而將$1[^[:digit:]]替換爲sda[^0-9]。下面是該做awk,而不是匹配在grep例子:

$ iostat -p -x 1 2 | grep 'sda ' 
sda    0.11  1.04 2.00 1.28 125.70 63.16 115.09  0.07 21.04 4.66 46.57 2.36 0.78 
sda    0.00  0.00 0.00 0.00  0.00  0.00  0.00  0.00 0.00 0.00 0.00 0.00 0.00 

$ iostat -p -x 1 2 | awk '/sda[^0-9]/ {++t} t==1 && /sda[^0-9]/ {print}' 
sda    0.11  1.04 2.00 1.28 125.70 63.16 115.09  0.07 21.04 4.66 46.57 2.36 0.78 

$ iostat -p -x 1 2 | awk '/sda[^0-9]/ {++t} t==2 && /sda[^0-9]/ {print}' 
sda    0.00  0.00 0.00 0.00  0.00  0.00  0.00  0.00 0.00 0.00 0.00 0.00 0.00 

$ iostat -p -x 1 4 | awk '/sda[^0-9]/ && t++ && t==2 {print}' 
sda    0.00  0.00 0.00 0.00  0.00  0.00  0.00  0.00 0.00 0.00 0.00 0.00 0.00 
+0

按照我的系統上的預期工作,但好像它將打印所有內容而不是一個字段? – mvd

+0

在我的回答中,前兩行輸出來自'iostat -x/dev/sda 1 2 | grep sda',即不跟awk。其他兩行輸出顯示NR == 1或NR == 2的結果。 (注意,我編輯的答案是使用sda而不是sdf,並且在一分鐘內會對此添加評論。) –

+0

@Mikhail,我添加了關於如何在awk中執行grep的註釋。對於這個應用程序來說,在awk中而不是在grep中匹配這些行並沒有什麼幫助,但在其他情況下,它會更靈活或更通用。 –

2

管它到tail -1,這將選擇最後一行。

iostat -p -x 1 2| grep $1[^[:digit:]] | awk '{print $9}' | tail -1 
2

結合headtail讓您從輸入選擇線的任何序列:

(cmd) | tail -n+2 | head -n 1 

獲取輸入的第二行不管命令的輸出有多長。