文本快排序出現(xiàn)的原因: 有時,你會需要將多行記錄組合而成的數(shù)據(jù)排序。 地址清單就是一個很好的例子,為了方便閱讀,地址記錄經(jīng)常會切斷,以一個或數(shù)個空行批次隔開,像這種數(shù)據(jù),沒有一定的排序鍵值位置可供 -k 選項(xiàng)使用,所以就引入了文本快排序。
案例:
我有一個文件 adress.txt,內(nèi)容為:
J Luo
Southeast University
Nanjing,China
\
Y Zhang
Victory University
Melbourne,Australia
\
D Hou
Beijing University
Beijing,China
\
B Liu
Shanghai Jiaotong University
Shanghai,China
\
C Lin
University of Toronto
Toronto,Canada
要求:對文本塊根據(jù)學(xué)校的名字 (每個文本塊的第二行) 進(jìn)行排序,結(jié)果仍然能以文本塊的格式輸出。
awk '{a[$2]=$0}END{for(i=1;i<=asorti(a,b);i++)print a[b[i]]}' ORS='\n\n' RS= FS='\n' adress.txt 這一種方法效率高,各種牛逼,看不明白十格什么 JB 意思。
第二種方式:awk 'BEGIN{FS="\n";RS=""}{print $1":"$2":"$3":"}' adress.txt|sort -t ":" -k2|tr ":" "\n",這種方式貌似比較平民,適合屌絲玩家。 那到底是什么意思呢?
首先使用 awk 命令將文本塊轉(zhuǎn)化成以下這樣:
J Luo:Southeast University:Nanjing,China
Y Zhang:Victory University:Melbourne,Australia
D Hou:Beijing University:Beijing,China
B Liu:Shanghai Jiaotong University:Shanghai,China
C Lin:University of Toronto:Toronto,Canada
然后使用 sort 命令按照學(xué)校 (也就是原文本的第二行) 排序。 排序后的結(jié)果為:
D Hou:Beijing University:Beijing,China
B Liu:Shanghai Jiaotong University:Shanghai,China
J Luo:Southeast University:Nanjing,China
C Lin:University of Toronto:Toronto,Canada
Y Zhang:Victory University:Melbourne,Australia
最后使用 tr “:” “\n” 命令,將排序后的文本轉(zhuǎn)化回來。
awk 的 FS: 輸入字段分隔符(缺省為space),相當(dāng)于 -F 選項(xiàng)
awk -F ':' '{print}' shcool.txt 和 awk 'BEGIN{FS=":"}{print}' shcool.txt 是一樣的
RS:輸入記錄分隔符,缺省為 "\n" 缺省情況下,awk 把一行看作一個記錄;如果設(shè)置了 RS,那么 awk 按照RS 來分割記錄,此處的意思是說將原文本看成是一條記錄。
例如,如果文件 c,cat c 為
hello world; I want to go swimming tomorrow;hiahia
運(yùn)行 awk 'BEGIN{RS =";"} {print}' c 的結(jié)果為
hello world
I want to go swimming tomorrow
hiahia
合理的使用 RS 和 FS 可以使得 awk 處理更多模式的文檔,例如可以一次處理多行,例如文檔 d ,cat d 的輸出為
1 2
3 4 5
\
6 7
8 9 10
11 12
\
hello
每個記錄使用空行分割,每個字段使用換行符分割,這樣的 awk 也很好寫
awk 'BEGIN{FS ="\n"; RS =""} {print NF}' d 輸出
2
3
1
而 tr 的意思是替換,將":" 替換成"\n"。