awk內建變數NR與FNR
awk 命令中NR表示從awk開始執行後,按照記錄分隔符讀取的資料次數,預設的記錄分隔符為換行符,因此預設的就是讀取的資料行數,NR可以理解為Number of Record的縮寫。
在awk處理多個輸入檔案的時候,在處理完第一個檔案後,NR並不會從1開始,而是繼續累加,因此就出現了FNR,每當處理一個新檔案的時候,FNR就從1開始計數,FNR可以理解為File Number of Record。
下面看兩個例子:
1,對於單個檔案NR 和FNR 的 輸出結果一樣的 :
# awk '{print NR,$0}' file1 1 a b c d 2 a b d c 3 a c b d #awk '{print FNR,$0}' file1 1 a b c d 2 a b d c 3 a c b d
2,但是對於多個檔案 :
# awk '{print NR,$0}' file1 file2 1 a b c d 2 a b d c 3 a c b d 4 aa bb cc dd 5 aa bb dd cc 6 aa cc bb dd # awk '{print FNR,$0}' file1 file2 1 a b c d 2 a b d c 3 a c b d 1 aa bb cc dd 2 aa bb dd cc 3 aa cc bb dd
NR和FNR的典型應用場景
現在有兩個檔案格式如下:
#cat account.data 張三|1 李四|2 #cat course.data 1|語文 1|數學 2|英語 2|化學
想要得到的結果是將使用者名稱,帳號和課程在同一行列印出來,如下:
張三|1|語文 張三|1|數學 李四|2|英語 李四|2|化學
執行如下程式碼
#awk -F \| 'NR==FNR{a[$2]=$0;next}{print a[$1]"|"$2}' account.data course.data
註釋:
由NR=FNR為真時,判斷當前讀入的是第一個檔案account.data,然後使用{a[$2]=$0;next}迴圈將account檔案的每行記錄都存入陣列a,並使用$2第2個欄位作為下標引用.
由NR=FNR為假時,判斷當前讀入了第二個檔案course.data,然後跳過{a[$2]=$0;next},對第二個檔案cdr的每一行都無條件執行{print a[$1]"|"$2},此時變數$1為第二個檔案的第一個欄位,與讀入第一個檔案時,採用第一個檔案第二個欄位$2為陣列下標相同.因此可以在此使用a[$1]引用陣列。
awk常用命令
1、列印檔案的第一列(域) : awk '{print $1}' filename
2、列印檔案的前兩列(域) : awk '{print $1,$2}' filename
3、列印完第一列,然後列印第二列 : awk '{print $1 $2}' filename
4、列印文字檔案的總行數 : awk 'END{print NR}' filename
5、列印文字第一行 :awk 'NR==1{print}' filename