2

我有我自己无法解决的文本处理问题,因此我需要更聪明的人的帮助。
我的虚拟文件示例如下所示:

Winter    Sally    Additional_text
Winter    Sally    Additional_text
Winter    Nicole    Additional_text  
Spring    Lucy    Additional_text
Spring    Lucy    Additional_text
Spring    Caroline    Additional_text
Spring    Caroline    Additional_text
Summer    Emma    Additional_text
Autumn    Rita    Additional_text
Autumn    Rita    Additional_text
Autumn    Cristina     Additional_text
Autumn    Lucy's_sister     Additional_text
Autumn    Lucy's_sister     Additional_text

我想:
对于每个第一列项目,计算第二列中有多少个不同的名称。但我只需要计算那些名称:1)至少出现两次和 2)至少有两个不同的名称(它们都至少出现两次)。
对于这样的输出:

Time    Counts 
Spring    2
Autumn    2

输出解释:
Winter两个不同的名字,但Nicole只出现一次——winter不报告;
其中Spring至少有两个不同的名称,并且每个名称至少出现两次 - 报告有多少不同的名称Spring;只有一个名字 -没有报道
; 在三个不同的名称中,但其中只有两个出现至少两次 - 仅用于和的计数。SummerSummer
AutumnRitaLucy's_sister


在 awk 和 bash 中 编辑我的解决方案:

cut -d " " -f 1 FILE | sort -u > names
for i in $(cat names)
do 
   grep ^$i FILE | 
   awk '{print $2}' | 
   sort | 
   uniq -c | 
   awk -v VAR="$i" '($1>=2) {print VAR}' | 
   sort | 
   uniq -c | 
   awk '($1>=2) {print $2"\t"$1}' 
done

这太笨拙和重复了,所以我想知道更简单的方法。

4

3 回答 3

2

这是应该适合您的 awk 命令:

awk '{sums[$1"~"$2]++} END {for (a in sums) {split(a, b, "~"); if (sums[a]>1) suma[b[1]]++;}
      for (k in suma) if (suma[k]>1) print k, suma[k]}' inFile
于 2013-06-11T10:55:30.467 回答
1
awk '{kc[$1 "-" $2]++ } 
     END { for (k in kc) { if (kc[k]>=2) {f[gensub("-.*","","g",k)]++}}
           for (kk in f) { if (f[kk]>=2 ) {print kk, f[kk]}}}' INPUTFILE

会为你工作。首先,它计算FIRSTCOL-SECONDCOL数组中“”出现的次数。然后在每次出现的文件末尾检查出现次数,如果它大于一,则将其存储FIRSTCOL在另一个数组中(作为键)并将其值加一。FIRSTVAL如果大于一,则打印每个及其值。我把标题留给你。

注意-:如果第一列中有任何 ' ',它将失败

于 2013-06-11T11:04:21.523 回答
1

这是使用GNU awk. 像这样运行:

awk -f ./script.awk file

内容script.awk

BEGIN {
    OFS="\t"
}
{
    a[$1][ b[$1,$2]++ ]++
}
END {
    print "Time", "Counts";
    for (i in a) {
        for (j in a[i]) {
            if (j >= 1 && a[i][j] >= 2) {
                print i, a[i][j]
            }
        }
    }
}

或者,这是单线:

awk '{ a[$1][ b[$1,$2]++ ]++ } END { print "Time", "Counts"; for (i in a) for (j in a[i]) if (j >= 1 && a[i][j] >= 2) print i, a[i][j] }' OFS="\t" file

结果:

Time    Counts
Autumn  2
Spring  2
于 2013-06-11T11:12:28.147 回答