Bash处理双列CSV:按第一列分组保留第二列高频行
如何在Bash中处理双列CSV:按第一列分组保留第二列高频行
核心解决方案(使用awk)
直接用awk的二维数组统计频率,按第一列分组处理,最终保留每组内第二列出现频率最高的行(频率相同的各留一行):
awk -F ',' ' # 统计每组内第二列值的出现次数 { count[$1][$2]++ } END { # 遍历每个第一列分组 for (key in count) { max_freq = 0 # 先找出当前组的最高频率 for (val in count[key]) { if (count[key][val] > max_freq) { max_freq = count[key][val] } } # 输出所有达到最高频率的行(每个值仅输出一次) for (val in count[key]) { if (count[key][val] == max_freq) { print key "," val } } } }' input.csv
逻辑说明
-F ',':指定CSV的分隔符为逗号count[$1][$2]++:用二维数组count记录每个第一列值($1)对应的第二列值($2)的出现次数- END块处理:
- 遍历所有第一列分组(
key) - 先遍历当前组的所有第二列值,找到最高出现频率
max_freq - 再次遍历当前组,输出所有出现次数等于
max_freq的行,确保每组内每个高频值只保留一行
- 遍历所有第一列分组(
示例验证
假设输入文件input.csv内容如下:
1234,000 1234,000 1234,000 1234,111 1234,111 5678,222 5678,222 5678,333 5678,333
执行命令后输出:
1234,000 5678,222 5678,333
保持原分组顺序的优化版本
如果需要保留原文件中第一列分组的出现顺序,可添加数组记录首次出现的顺序:
awk -F ',' ' # 记录第一列分组的首次出现顺序 !seen[$1]++ { order[++n] = $1 } # 统计频率 { count[$1][$2]++ } END { # 按原顺序遍历分组 for (i=1; i<=n; i++) { key = order[i] max_freq = 0 for (val in count[key]) { if (count[key][val] > max_freq) { max_freq = count[key][val] } } for (val in count[key]) { if (count[key][val] == max_freq) { print key "," val } } } }' input.csv
内容的提问来源于stack exchange,提问作者Hashim Aziz
相关产品推荐
相关产品推荐

