我有一个大文件,有 50 列和 100K 行,由 | 分隔。现在 $2(col 2) 具有多种类型的 $1(col 1) 值,这意味着 col 2 将重复。所以我已经对文件进行了排序。我现在需要根据以下条件提取/过滤结果文件: $1 是第 1 列 $2 是第 2 列
$2 和 $1 之间存在一对多关系
条件 1 :当 $2 具有 $1 两种类型时($2 的 $1 值大于 8000 且小于 8000),则选择给定 $2 的 $1 < 8000 的完整行(第 2 列)
条件 2:如果 $2 只有 $1 >= 8000,则选择完整的行,其中 $1 是给定 $2(第 2 列)中最小的行 例如:源文件 在下面的示例中,我们有 3 种类型的 $2(1234,123 和 456)现在 1234 在第 1 列中有 3 种类型的值 ($1),意味着大于和小于 8000。因此,我们为 $1<8000 的值选择了完整的行。
对于 123 和 465,我们第 1 列的值仅大于 8000($1>80000),因此我们选择了最新的行(基于第 8 列的值较高)。
样本文件
4000|1234||||||23
5000|1234||||||40
9000|1234||||||25
10000|123|||||||21
9000|123|||||||22
22000|456|||||||27
15000|456|||||||29
结果文件将有:
4000|1234||||||23
5000|1234||||||40
9000|123|||||||22
15000|456|||||||29
请指教。提前致谢。
答案1
尝试(你是你的文件)
sort -n -t\| -k2 -k1 < u |
awk -F\| '$1 < 8000 { a[$2]++ ; print }
$1 >= 8000 { if ( !a[$2] && ( !e[$2] || e[$2]<$8 )) {u[$2]=$0;e[$2]=$8;} ; }
END { for ( i in u ) print u[i] ;}'
给出
4000|1234||||||23
5000|1234||||||40
15000|456||||||29
9000|123||||||22
在哪里
-t\|
并-F\|
指示 sort 和 awk 用作|
分隔符-k2
-k1
:按第二个字段排序,然后按第一个字段排序|
排序行中应该是行中的最后一个字符$1 < 8000 { a[$2]++ ; print }
如果低于 8000,则打印行并记住 2 美元的值$1 >= 8000 { ... }
如果高于,则存储最高值END { for ( i in u ) print u[i] ;}
退出时转储所有值您可能需要重新排序。
第 2 行条件可以简化(通过将 if 条件置于 {} 之外)
您的测试中的某些行有 9 个字段。
请注意,该命令可以是一行
... | sort -n -t\| -k2 -k1 | awk -F\| '...'