在数字之间找到模式并对它们求和?

find pattern in between numbers and sum them?

我的档案:

chr2    10145622        10170989        11
chr7    15682126        15682183        28
chr18   48064121        48064222        10,7
chr23   20637149        20637247        824,86
chr25   2063714         2072977         824,80,62,2
chr16   48064100        48064272        10,9

期望的输出:

chr2    10145622        10170989        11
chr7    15682126        15682183        28
chr18   48064121        48064222        17
chr23   20637149        20637247        910
chr25   2063714 2072977 968
chr16   48064100        48064272        19

我试过了:

cat test.bed | sed 's/\,/\t/g' | awk '{OFS="\t"; print ,,,+NF}'

但它也对空白列求和,这是不正确的。确实如此,因为我已将“,”替换为制表符。

如果我们知道最后几列,效果很好

cat test.bed | sed 's/\,/\t/g' | awk '{OFS="\t"; print ,,,+++}'

但是,我使用 NF 表示从第 4 列到最后一列,假设我们不知道文件中有多少个模式及其编号。

您可以拆分最后一个字段并对其各部分求和:

$ awk '{n=split($NF, a, ","); for (i=1;i<=n;i++) s+=a[i]; $NF=s; s=0}1' file
chr2 10145622 10170989 11
chr7 15682126 15682183 28
chr18 48064121 48064222 17
chr23 20637149 20637247 910
chr25 2063714 2072977 968
chr16 48064100 48064272 19

要处理 input/output 字段分隔符,您可以说 BEGIN {FS=OFS="\t"},例如。

说明

  • n=split($NF, a, ",") 根据逗号分隔符拆分最后一个字段。这样,您就有了一个数组 a,其中包含与切片部分一样多的值。 split()returns的数量"pieces",所以我们存储它。
  • for (i=1;i<=n;i++) s+=a[i]; $NF=s; s=0 遍历 a 中的项目列表并将它们加到变量 s 中。 (注意:for (i in a) 也适用于这种情况,顺序无关紧要)。然后,将最后一个字段设置为此值并重置计数器。
  • 1 当它计算为 True 时,它​​执行默认的 awk 操作:打印当前行。

awk有一个split函数,就是把一个字符串根据一个RE进行拆分,然后把各个部分放到一个数组变量中,你可以split每一行的最后一个字段一个逗号,然后对数组的元素求和

NF==4{split(,arr,',');  = 0; for(i in arr) +=arr[i];}
1

NB1 当且仅当 $4
中的数字之间没有空格时才有效 NB2 最后一个 1 强制打印当前行