将每个列值除以矩阵中的第一个值

时间:2014-02-21 07:19:20

标签: r shell

我有一个如下矩阵:

totalreadcount  36  27  13  13
bna-miR172e-3p  0   1   4805    2767
bna-miR167a 4   26  11818   15776
bna-miR172a 0   0   4302    2464
bna-miR319b-3p  102 60  94  51
bna-miR156a 0   0   139 59
bna-miR167d 38  108 55389   58479

我想将列的每个值除以其第一个值。例如:在第二列36中是第一个值,我需要将剩余值(如0,4,102,0,38)除以36,与其他列相同。 矩阵大小很大,所以任何人都可以通过shell脚本或R语言脚本来帮助我进行这样的计算。

2 个答案:

答案 0 :(得分:2)

这是一个解决方案:

> mat <- matrix(1:15, 5, 3)
> mat
     [,1] [,2] [,3]
[1,]    1    6   11
[2,]    2    7   12
[3,]    3    8   13
[4,]    4    9   14
[5,]    5   10   15
> mat[-1, ] / mat[1, ] # divide all rows except the first one by the first row
          [,1]      [,2]      [,3]
[1,] 2.0000000 1.1666667  1.090909
[2,] 0.5000000 0.7272727 13.000000
[3,] 0.3636364 9.0000000  2.333333
[4,] 5.0000000 1.6666667  1.363636

答案 1 :(得分:1)

使用awk你可以这样做:

awk 'NR==1 && NF>1 {$1=$1; for (i=2; i<=NF; i++) a[i]=$i}
     NR>1{for (i=2; i<=NF; i++) $i=$i/a[i]} 1' file

totalreadcount 36 27 13 13
bna-miR172e-3p 0 0.037037 369.615 212.846
bna-miR167a 0.111111 0.962963 909.077 1213.54
bna-miR172a 0 0 330.923 189.538
bna-miR319b-3p 2.83333 2.22222 7.23077 3.92308
bna-miR156a 0 0 10.6923 4.53846
bna-miR167d 1.05556 4 4260.69 4498.38

<强>解释

在第一个区块中我有:

NR==1 && NF>1 {$1=$1; for (i=2; i<=NF; i++) a[i]=$i}

仅针对文件的第一个记录运行,并将#2以后的每个列存储在数组a中。 $1=$1是改变记录多余空白间距的简单技巧。

在第二块我有:

NR>1{for (i=2; i<=NF; i++) $i=$i/a[i]}

对于#2以后的每一列,我们将列值除以存储在a中的相应数组值。最后1用于在stdout上打印值。