awk完全分开重复和非重复

时间:2014-07-24 19:25:47

标签: awk duplicates

如果我们有输入:

TargetIDs,CPD,Value,SMILES
95,CPD-1111111,-2,c1ccccc1
95,CPD-2222222,-3,c1ccccc1
95,CPD-2222222,-4,c1ccccc1
95,CPD-3333333,-1,c1ccccc1N

现在我们想根据第四列(微笑)分离重复和非重复

重复:

95,CPD-1111111,-2,c1ccccc1
95,CPD-2222222,-3,c1ccccc1
95,CPD-2222222,-4,c1ccccc1 

非重复

95,CPD-3333333,-1,c1ccccc1N

现在,以下尝试可以将副本分开而没有任何问题。但是,第一次出现的副本仍将包含在非重复文件中。

BEGIN { FS = ","; f1="a"; f2="b"}

{
# Keep count of the fields in fourth column
count[$4]++;

# Save the line the first time we encounter a unique field
if (count[$4] == 1)
    first[$4] = $0;


# If we encounter the field for the second time, print the
# previously saved line
if (count[$4] == 2)
    print first[$4] > f1 ;

# From the second time onward. always print because the field is
# duplicated
if (count[$4] > 1)
    print > f1;

if (count[$4] == 1)      #if (count[$4] - count[$4] == 0)    <= change to this doesn't work
    print first[$4] > f2;

尝试重复输出结果:

95,CPD-1111111,-2,c1ccccc1
95,CPD-2222222,-3,c1ccccc1
95,CPD-2222222,-4,c1ccccc1

尝试

的非重复输出结果
TargetIDs,CPD,Value,SMILES
95,CPD-3333333,-1,c1ccccc1N
95,CPD-1111111,-2,c1ccccc1

我可以知道是否有任何大师可能有评论/解决方案?感谢。

4 个答案:

答案 0 :(得分:4)

我会这样做:

awk '
    NR==FNR {count[$2] = $1; next} 
    FNR==1  {FS=","; next} 
    {
        output = (count[$NF] == 1 ? "nondup" : "dup")
        print > output
    }
' <(cut -d, -f4 input | sort | uniq -c) input

process substitution将预处理文件并对第4列执行计数。然后,您可以处理该文件并确定该行是否“重复”。


全部用awk:Ed Morton展示了一次收集数据的方法。这是一个2遍解决方案,几乎与我上面的例子相同

awk -F, '
    NR==FNR {count[$NF]++; next} 
    FNR==1  {next} 
    {
        output = (count[$NF] == 1 ? "nondup" : "dup")
        print > output
    }
'  input  input

是的,输入文件被给出两次。

答案 1 :(得分:2)

$ cat tst.awk
BEGIN{ FS="," }
NR>1 {
    if (cnt[$4]++) {
        dups[$4] = nonDups[$4] dups[$4] $0 ORS
        delete nonDups[$4]
    }
    else {
        nonDups[$4] = $0 ORS
    }
}
END {
    print "Duplicates:"
    for (key in dups) {
        printf "%s", dups[key]
    }

    print "\nNon Duplicates:"
    for (key in nonDups) {
        printf "%s", nonDups[key]
    }
}

$ awk -f tst.awk file
Duplicates:
95,CPD-1111111,-2,c1ccccc1
95,CPD-2222222,-3,c1ccccc1
95,CPD-2222222,-4,c1ccccc1

Non Duplicates:
95,CPD-3333333,-1,c1ccccc1N

答案 2 :(得分:1)

此解决方案仅在重复项组合在一起时才有效。

awk -F, '
  function fout(    f, i) {
    f = (cnt > 1) ? "dups" : "nondups"
    for (i = 1; i <= cnt; ++i)
      print lines[i] > f
  }
  NR > 1 && $4 != lastkey { fout(); cnt = 0 }
  { lastkey = $4; lines[++cnt] = $0 }
  END { fout() }
' file

答案 3 :(得分:0)

小晚了 我在awk中的版本

awk -F, 'NR>1{a[$0":"$4];b[$4]++}
        END{d="\n\nnondupe";e="dupe"
        for(i in a){split(i,c,":");b[c[2]]==1?d=d"\n"i:e=e"\n"i} print e d}' file

另一个建造类似于格伦杰克曼但都在awk

awk -F, 'function r(f) {while((getline <f)>0)a[$4]++;close(f)}
BEGIN{r(ARGV[1])}{output=(a[$4] == 1 ? "nondup" : "dup");print >output} ' file