使用头文件基于标头从数据文件中提取列

时间:2016-08-19 16:31:19

标签: bash awk

我有一个大数据文件(不是csv),其中包含许多带标题行的列。列标题是包含字母和数字的字符串。我想编写一个脚本,根据标题提取数据列,如果标题存在于第二个文件中。我研究了这个问题,并根据AWK extract columns from file based on header selected from 2nd file的答案编写了一个改编的剧本。我理解它所做的很好的一部分,但我承认我完全不理解它。我知道它是为csv文件设计的......我尝试将它与我的文件一起使用,但我无法让它工作。这是代码(包含在bash脚本中):

(注意:$ motif_list和$ affinity_matrix是两个文件的路径,之前已在bash脚本中定义过)

 43 awk -v motif_list="$motif_list" -v affinity_matrix="$affinity_matrix" '
 44         BEGIN {
 45                 j=1
 46                 while ((getline < motif_list) > 0)
 47                 {
 48                         col_names[j++] = $1
 49                 }
 50                 n=j-1;
 51                 close(motif_list)
 52                 for (i=1; i<=n; i++) s[col_names[i]] = i
 53               }       
 54 
 55         NR==1 {
 56                 for (f=1; f<=NF; f++)
 57                         if ($f in s) c[s[$f]]=f
 58                 next
 59               }
 60 
 61         {
 62                 sep=" "
 63                 for (f=1; f<=n; f++)
 64                         {
 65                                 printf("%c%s",sep,$c[f])
 66                                 sep=FS
 67                         }
 68                 print " "
 69         }' "$affinity_matrix" > $affinity_columns

(我也将分隔符从“”更改为“”,但这可能不是正确的方法)

例如,以下是示例输入和输出表:

输入:

A   B   C   D   E   F
1   2   3   4   5   6
1   2   3   4   5   6
1   2   3   4   5   6
1   2   3   4   5   6
1   2   3   4   5   6

输出:

A   C   
1   3   
1   3   
1   3   
1   3   
1   3   

非常感谢任何输入!

由于

1 个答案:

答案 0 :(得分:1)

一般方法(由于您未提供任何样本输入/输出而未经测试)是:

awk '
NR==FNR { names[$0]; next }
FNR==1 {
    for (i=1;i<=NF;i++) {
        if ($i in names) {
            nrs[i]
        }
    }
}
{
    c = 0
    for (i=1;i<=NF;i++) {
        if (i in nrs) {
            printf "%s%s", (c++ ? OFS : ""), $i
        }
    }
    if (c) {
        print ""
    }
}
' motif_list affinity_matrix