使用awk过滤行

被过滤的数据

  1. MarkerName Allele1 Allele2 Freq1 FreqSE P-value Chr Pos
  2. rs2326918 a g 8510 0001 5255 6 130881784
  3. rs2439906 c g 0316 0039 8997 10 6870306
  4. rs10760160 a c 5289 0191 8107 9 123043147
  5. rs977590 a g 9354 0023 8757 7 34415290
  6. rs17278013 t g 7498 0067 3595 14 24783304
  7. rs7852050 a g 8814 0006 7671 9 9151167
  8. rs7323548 a g 0432 0032 4555 13 112320879
  9. rs12364336 a g 8720 0015 4542 11 99515186
  10. rs12562373 a g 7548 0020 6151 1 164634379

我们想要做的是Chr当它等于 6 时从(第 7 列)获取行,并且Pos当值在 11000000 和 25000000 之间时从(第 8 列)获取行。

例如,我们知道我们的数据中有 8 个由制表符分隔的列,但是如果你不知道有多少列,你可以通过一些awk找到它:

  1. > awk "{print NF}" < rumenz.txt | uniq

8

NF是一个 AWK 内置变量,它代表_字段数_。我们通过管道将其传递给,uniq因为默认行为将打印每行的列数,并且由于每行具有相同的列数,因此uniq会将其减少为一个数字。

打印字段和搜索

我们还可以使用 awk来选择和打印文件的一部分。让我们现在这样做。

  1. > awk '{print $1 $2}' rumenz.txt
  1. rs11058339t
  2. rs7338610t
  3. rs882601t
  4. rs13290449t
  5. rs2941056a
  6. rs10444526a
  7. rs12190167a
  8. rs1125337a
  9. rs7911101a
  10. rs13053206c
  11. rs697690t
  12. rs12447687t
  13. rs2402752t
  14. rs12042911a
  15. ...

请注意,输出没有格式。有很多方法可以在 awk中格式化和构建输出。查看awk用户指南上的打印部分以获取更多信息。

现在我们已经选择了几列来打印出来,让我们使用awk 来搜索一个特定的东西——我们知道数据集中存在的一个数字。请注意,如果你指定要打印哪些字段,awk将默认打印与搜索匹配的整行。

  1. > awk '/2410626/' rumenz.txt
  1. rs4853805 a t 2107 0029 4229 2 2410626

我们可以匹配一个字符串模式或正则表达式,而不是匹配一个唯一的数字。在这种情况下,awk 将返回与模式匹配的每一行。在我们上面的例子中,这个数字在数据文件中出现一次,但我们可以使用正则表达式或范围模式来代替。有关在 awk 中查找模式的更多信息,请查看awk 指南的模式、操作和变量部分。

根据字段值过滤行

现在我们知道如何访问字段(列)并在我们的文档中查找模式,但是我们如何控制要搜索的内容和位置?我们最初的问题要求我们查看该Chr字段以仅获取值为 6 的行。然后我们希望查看该Pos字段以获取这些值介于 11000000 和 25000000 之间的行。要在 awk 中执行此操作,我们需要使用在if同一个条件表达式一起控制语句。

  1. > awk '{ if ($7 == 6) { print } }' rumenz1-txt | head
  1. rs2326918 a g 8510 0001 5255 6 130881784
  2. rs16877977 a g 1302 0048 05945 6 16494324
  3. rs7763812 a t 9815 0008 05328 6 104042808
  4. rs222555 c g 3720 0051 7756 6 95272331
  5. rs9450727 t c 6193 0106 08575 6 88293919
  6. rs12200899 t c 7683 0075 7118 6 66215503
  7. rs990018 t c 0201 0000 6292 6 68825590
  8. rs1344178 a c 6250 0016 7234 6 118804141
  9. rs12529570 c g 1987 0148 266 6 110283483
  10. rs3130560 t g 2706 0242 2365 6 31205432

上面,我们使用关键字if,然后使用条件表达式($7 == 6),基于$7我们要测试的列变量。这里的$表示我们正在处理一个变量,在这种情况下,awk 知道这$7意味着我们数据集中的第 7 个字段。同样,$6将意味着第 6 个字段,依此类推。==经常在编程语言中用于测试相等性,因为单个=经常用于对象分配。我们在这里说的是,当我们在这个文件中逐行进行时,如果第 7 列中的值等于 6,则匹配为真,并且该行包含在输出中。

现在我们要在Pos列上测试条件的另一部分。这次我们将使用>=运算符来测试第 8 列中的值是否大于或等于 11000000。

  1. > awk '{ if($8 >= 11000000) { print }}' rumenz.txt | head
  1. MarkerName Allele1 Allele2 Freq1 FreqSE P-value Chr Pos
  2. rs2326918 a g 8510 0001 5255 6 130881784
  3. rs10760160 a c 5289 0191 8107 9 123043147
  4. rs977590 a g 9354 0023 8757 7 34415290
  5. rs17278013 t g 7498 0067 3595 14 24783304
  6. rs7323548 a g 0432 0032 4555 13 112320879
  7. rs12364336 a g 8720 0015 4542 11 99515186
  8. rs12562373 a g 7548 0020 6151 1 164634379
  9. rs17706069 a t 8055 0537 993 16 27095047
  10. rs17035887 a g 0588 0072 6673 2 46983448

到目前为止,我们已经确认我们可以使用ifawk 中的语句来返回满足条件的行。查看有关在 AWK 中使用控制语句的文档,了解更多使用条件进行决策的方法。

下一步是将这些条件表达式与第三个(小于 25000000)组合起来,一次性完成所有过滤。为此,我们需要在条件表达式中使用布尔运算符。让我们先对上面算出的两个条件表达式进行尝试。

  1. > awk '{ if(($7 == 6) && ($8 >= 11000000)) { print } }' rumenz.txt | tail
  1. rs9320690 a g 5342 0041 9136 6 119812605
  2. rs483727 t c 2512 0052 1624 6 81681348
  3. rs754997 t g 8192 0091 6605 6 133635869
  4. rs2073214 t c 1465 0007 1076 6 144123302
  5. rs12195885 a c 0224 0000 9662 6 23600679
  6. rs6924121 t c 6988 0031 4138 6 165249220
  7. rs11961870 a c 2470 0094 9404 6 143943842
  8. rs9476984 c g 0711 0014 9935 6 16036569
  9. rs9382099 t c 1443 0043 7554 6 52328752
  10. rs2504065 a g 4974 0009 3366 6 152136860

我们使用 boolean and && here(其他运算符是||for or!for not)来组合我们的两个条件语句。现在让我们将第二列$8条件 (<=25000000) 添加到 if 语句中。

  1. > awk '{ if(($7 == 6) && ($8 >= 11000000 && $8 <= 25000000)) { print } }' rumenz.txt
  1. rs16877977 a g 1302 0048 05945 6 16494324
  2. rs7767788 t c 6144 0042 3234 6 14098813
  3. rs12523811 a c 5216 0055 2504 6 17941531
  4. rs12199382 a g 4045 0113 7856 6 22435109
  5. rs9465281 c g 0719 0105 1794 6 19326722
  6. rs13196524 t c 9426 0209 8672 6 22356754
  7. rs12195885 a c 0224 0000 9662 6 23600679
  8. rs9476984 c g 0711 0014 9935 6 16036569

返回笔记列表
入门小站