首页 > 解决方案 > 如何获取具有特定列值的csv文件的前n行?

问题描述

在 Kaggle 中,我有一个这样的 csv 文件:

ip,app,device,os,channel,click_time,attributed_time,is_attributed
83230,3,1,13,379,2017-11-06 14:32:21,,0
17357,3,1,19,379,2017-11-06 14:33:34,,1
35810,3,1,13,379,2017-11-06 14:34:12,,0
45745,14,1,13,478,2017-11-06 14:34:52,,0
161007,3,1,13,379,2017-11-06 14:35:08,,1
18787,3,1,16,379,2017-11-06 14:36:26,,0
103022,3,1,23,379,2017-11-06 14:37:44,,0
114221,3,1,19,379,2017-11-06 14:37:59,,0

现在我想获取“is_attributed”为 1 的前 200 行。请问如何使用“cut”和其他实用程序来做到这一点?

标签: bashawkgrepcut

解决方案


awk您可以一次性完成过滤和线路限制:

awk -F, -v limit=200 '$NF == 1 { if (++n > limit) exit; print }' file.csv
  • -F, - 分隔符是逗号
  • -v limit=200 - 初始化要在 awk 命令中使用的变量
  • $NF == 1 - 仅当最后一个字段的值为 1 时才采取行动
  • if (++n > limit) exit- 一旦我们收集到所需的行数,就停止读取输入

在上面的解决方案中,我们隐式地跳过了标题行,因为标题不以 1 结尾。为了更健壮,我们可以使其显式:

awk -F, -v limit=200 'NR  == 1 { next }
                      $NF == 1 { if (++n > limit) exit; print }' file.csv

grep ... | head -n由于以下几个原因,这是一个更好的解决方案:

  • 这里不涉及管道(和额外的分叉)
  • 我们一到达线路限制就停下来;如果输入文件非常大,这可能会产生巨大的差异(grep -m也可以这样做)
  • 很容易将此解决方案扩展到任意领域,而不仅仅是第一个或最后一个
  • 如果分隔符是多字符的,或者需要通过正则表达式匹配,那么 awk 很容易处理它

相关帖子:


推荐阅读