使用awk创建一个数组并将其传递给第二个awk操作

时间:2014-03-25 09:31:18

标签: bash shell awk

我有一个列文件,我想要打印所有不包含字符串SOL的行,并且只打印包含SOL的行但是第5列<1.2或&gt; 4.8。

该文件的结构为:MOLECULENAME ATOMNAME X Y Z

示例:

  151SOL     OW 6554   5.160   2.323   4.956  
  151SOL    HW1 6555   5.188   2.254   4.690  ----> as you can see this atom is out of the   
  151SOL    HW2 6556   5.115   2.279   5.034  threshold, but it need to be printed

我想的是用我想要的所有MOLECULENAME保存一个向量,然后告诉awk将保存在向量“a”中的所有MOLECULENAME与文件匹配,并打印完整的输出。 (如果我只做第一个awk,我最终在thershold附近有坏原子连接)

问题是我必须将矢量从第一个awk传递到第二个......我用[]尝试了这个,但当然它不起作用。

我该怎么做?

这是我到目前为止的代码:

a[] = (awk 'BEGIN{i=0} $1 !~ /SOL/{a[i]=$1;i++}; /SOL/ && $5 > 4.8 {a[i]=$1;i++};/SOL/ &&$5<1.2 {a[i]=$1;i++}')

awk -v a="$a[$i]" 'BEGIN{i=0} $1 ~ $a[i] {if (NR>6540) {for (j=0;j<3;j++) {print $0}} else {print $0} 

3 个答案:

答案 0 :(得分:1)

您可以使用文件上的排序将所有相同的分子名称放在一行中,然后运行此AWK,它基本上使用printf在同一行上打印,直到找到不同的分子名称。然后,新行开始。第二个AWK脚本用于检测哪些分子名称在原始文件中有3个有效行。我希望这可以帮助您解决问题

sort your_file | awk 'BEGIN{ molname=""; } ( $0 !~ "SOL" || ( $0 ~ "SOL" && ( $5<1.2 || $5>4.8 ) )  ){ if($1!=molname){printf("\n");molname=$1}for(i=1;i<=NF;i++){printf("%s ",$i);}}' | awk 'NF>12 {print $0}'

答案 1 :(得分:0)

awk '!/SOL/ || $5 < 1.2 || $5 > 4.8' inputfile.txt

打印(默认行为)行,其中:

  • &#34; SOL&#34;找不到
  • 找到SOL并且第五列&lt; 1.2
  • 找到SOL并且第五列&gt; 4.8

答案 2 :(得分:0)

解决了!感谢所有人,这是我如何解决它。

    #!/bin/bash
    file=$1
    awk 'BEGIN {molecola="";i=0;j=1;}  
    {if ($1 !~ /SOL/) {print $0}    
    else if ( $1 != molecola && $1 ~ /SOL/ ) {   
    for (j in arr_comp) {if( arr_comp[j] < 1.2 || arr_comp[j] > 5) {for(j in arr_comp)                                 {print   arr_mol[j] };break}}  
    delete(arr_comp)  
    delete(arr_mol)  
    arr_mol[0]=$0   
    arr_comp[0]=$5  
    molecola=$1  
    j=1     
    }   
    else {arr_mol[j]=$0;arr_comp[j]=$5;j++} }' $file