【问题标题】:Column aggregation in linuxlinux中的列聚合
【发布时间】:2012-02-17 13:42:13
【问题描述】:

我有这种格式的大文本文件:

aaa bbb 1      
aaa ccc 2      
aaa ddd 3      
bbb ww 1      
bbb kio 3      

我想聚合它,结果应该是:

aaa bbb 1/6  
aaa ccc 2/6  
aaa ddd 3/6  
bbb ww 1/4  
bbb kio 3/4  

第三列 - 概率 p(y|x)

我应该如何使用 awk、sed 来做到这一点?

【问题讨论】:

  • 假设 x 是第一列,y 是第二列,输出中的第三列不是 (x, y) 对的概率。相反,它是给定 x 时 y 的条件概率,P(y | x)。
  • 是的,你是对的,抱歉打错了

标签: file bash sed awk aggregation


【解决方案1】:
awk 'NR==FNR{a[$1]+=$3;next}{printf("%s/%d\n",$0,a[$1])}' ./infile ./infile

输出

$ awk 'NR==FNR{a[$1]+=$3;next}{printf("%s/%d\n",$0,a[$1])}' ./infile ./infile
aaa bbb 1/6
aaa ccc 2/6
aaa ddd 3/6
bbb ww 1/4
bbb kio 3/4

【讨论】:

    【解决方案2】:

    您可以分两次完成。使用以下命令生成 a.tmp

    { total[$1] += $3}
    END {for (group in total) {print group, total[group]}}
    

    这会创建一个包含组总数的临时文件:

    bbb 4
    aaa 6
    

    然后进行第二次传递:

    BEGIN {
        while ((getline line < "a.tmp") > 0) {
            split(line, fields, " ")
            group[fields[1]] = fields[2]
        }
        close("a.tmp")
    }
    {   printf("%s/%d\n", $0, group[$1]) }
    

    这会产生您正在寻找的输出:

    aaa bbb 1/6
    aaa ccc 2/6
    aaa ddd 3/6
    bbb ww 1/4
    bbb kio 3/4
    

    【讨论】:

      【解决方案3】:

      这可能对你有用:

      awk 'func p(){for(x=0;x<c;x++)printf("%s/%d\n",l[x],t);k=$1;t=c=0};BEGIN{k=$1};$1!=k{p()};{l[c++]=$0;t+=$3};END{p()}' file
      aaa bbb 1/6
      aaa ccc 2/6
      aaa ddd 3/6
      bbb ww 1/4
      bbb kio 3/4
      

      注意假设文件是​​按键预排序的。

      【讨论】:

        猜你喜欢
        • 2010-10-01
        • 2023-01-10
        • 1970-01-01
        • 2017-08-04
        • 2021-03-23
        • 1970-01-01
        • 1970-01-01
        • 2017-09-03
        • 1970-01-01
        相关资源
        最近更新 更多