在排序算法里有個重要的問題: 是否穩(wěn)定? 這個問題指的是: 相同的記錄輸入順序是否在輸出時也可保持原狀? 當你以多鍵值為記錄進行排序,或是以管道處理時,排序穩(wěn)定性就非常重要了。我們先來驗證一下。
sort -t_ -k1,1 -k2,2 <<EOF
\> one_two
\> one_two_three
\> one_two_four
\> one_two_five
\>EOF
輸出為:
one_two
one_two_five
one_two_four
one_two_three
每條記錄內(nèi)的排序字段都相同,但是輸出與輸入不一致,所以我們說 sort 不是穩(wěn)定的排序。幸好: 我們可以通過--stable 選項補救這個問題,設(shè)置此選項,就會穩(wěn)定了。
sort --stable -t_ -k1,1 -k2,2 << EOF
輸出為:
one_two
one_two_three
one_two_four
one_two_five
sort
命令的重要性絕對能在 linux 中拍到前十。
有時,將數(shù)據(jù)流里連續(xù)重復(fù)的記錄刪除是必要的。使用 sort -u
的消除操作十一局匹配的鍵值,而非匹配的記錄。
uniq
命令提供了另外一種過濾數(shù)據(jù)的方式: 常用于管道中,用來刪除已使用 sort 排序完成的重復(fù)記錄。
sort ... | uniq | ...
uniq [OPTION]… [INPUT [OUTPUT]]
從文件中去除或刪除重復(fù)的行,在功能上和 sort -u
類似。
常用選項:
-u
: 只顯示不重復(fù)的行-d
: 只顯示重復(fù)的行-c
: 打印每一行出現(xiàn)的次數(shù)-fn
: 忽略前 n 個域例如: 我有一個文件:unip.txt
tres
unus
duo
tres
duo
tres
使用 sort uniq.txt |uniq
命令顯示唯一的,排序后的記錄,重復(fù)則僅取唯一行。
輸出為:
duo
tres
unus
使用 sort uniq.txt | uniq -c
命令計數(shù)唯一的,排序后的記錄,說白了就是統(tǒng)計各行文本出現(xiàn)的次數(shù)
2 duo
3 tres
1 unus
代表的意思是說 duo 出現(xiàn)了兩次,tres 出現(xiàn)了三次,unus 出現(xiàn)了一次。
使用 sort uniq.txt | uniq -d
命令僅顯示重復(fù)的記錄
輸出結(jié)果為:
duo
tres
使用 sort uniq.txt | uniq -u
命令僅顯示未重復(fù)的記錄
輸出結(jié)果為:unus
cat file1.txt file2.txt | sort | uniq > file.txt
cat file1.txt file2.txt | sort | uniq -d >file.txt
cat file1.txt file2.txt | sort | uniq -d >temp.txt
cat file1.txt temp.txt | sort | uniq -u >file.txt
文本中的重復(fù)行,基本上不是我們所要的,所以就要去除掉。linux 下有其他命令可以去除重復(fù)行,但是我覺得 uniq 還是比較方便的一個。使用 uniq 的時候要注意以下二點
sort
命令進行組合使用,因為 uniq 不會檢查重復(fù)的行,除非它們是相鄰的行。如果您想先對輸入排序,使用 sort -u
。uniq 的所有選項:
-c
, --count // 在每行前加上表示相應(yīng)行目出現(xiàn)次數(shù)的前綴編號-d
, --repeated // 只輸出重復(fù)的行-D
, --all-repeated // 只輸出重復(fù)的行,不過有幾行輸出幾行-f
, --skip-fields=N //-f 忽略的段數(shù),-f 1 忽略第一段-i
, --ignore-case // 不區(qū)分大小寫-s
, --skip-chars=N // 根 -f 有點像,不過 -s 是忽略,后面多少個字符 -s 5 就忽略后面 5 個字符-u
, --unique // 去除重復(fù)的后,全部顯示出來,根 mysql 的 distinct 功能上有點像-z
, --zero-terminated end lines with 0 byte, not newline-w
, --check-chars=N // 對每行第 N 個字符以后的內(nèi)容不作對照--help
// 顯示此幫助信息并退出--version
// 顯示版本信息并退出