输入:
line1 a gh
line2 a dd
line3 c dd
line4 a gg
line5 b ef
期望的输出:
line3 c dd
line5 b ef
也就是说,我想仅在第2列中没有其他行包含相同值的情况下输出行。我认为我可以通过组合排序(例如sort -k2,2输入)和uniq来实现这一点,但似乎使用uniq我只能跳过左边的列(-f避免比较前N个字段)。当然有一些直接的方法来使用awk或其他东西。
答案 0 :(得分:3)
您可以将此作为两遍awk脚本执行此操作:
awk 'NR==FNR{a[$2]++;next} a[$2]<2' file file
一旦递增一个数组中的计数器,其键是每行的第二个字段,然后再次运行,只打印那些计数器小于2的行。
您需要多次读取该文件,因为在第一次读取期间的任何时候,您都不可能知道文件后面是否会有该行的第二个字段的另一个实例。
答案 1 :(得分:2)
以下是一次通过awk
解决方案:
awk '{a1[$2]++;a2[$2]=$0} END{for (a in a1) if (a1[a]==1) print a2[a]}' file
然而,文件的原始顺序将丢失。
答案 2 :(得分:1)
你可以将awk,grep,sort和uniq组合成一个快速的单行:
grep -v "^[^ ]* $(awk '{print $2}' input.txt | sort | uniq -d) " input.txt
编辑,以避免正则表达式,\ +和\ backreferences:
grep -v "^[^ ]* $(awk '{print $2}' input.txt | sort | uniq -d | sed 's/[^+0-9]/\\&/g') " input.txt
答案 3 :(得分:1)
替代awk
以证明它仍然可以使用sort和uniq(这里有选项-u
),但是设置正确的格式需要一些杂耍(装饰/做东西/ undecorate模式)。
$ paste file <(cut -d' ' -f2 file) | sort -k2 | uniq -uf3 | cut -f1
line5 b ef
line3 c dd
作为副作用,您将丢失原始排序顺序,如果您添加行号,也可以恢复...