使用特定模式选择列然后找到总和和比率

Selecting columns using specific patterns then finding sum and ratio

我想根据以下数据计算总和值和比率值。 (实际数据包含超过 200,000 列和 45000 行(行))。

为了清楚起见,我只给出了简单的数据格式。

#Frame  BMR_42@O22  BMR_49@O13  BMR_59@O13  BMR_23@O26  BMR_10@O13  BMR_61@O26  BMR_23@O25 
 1      1           1           0           1           1           1           1
 2      0           1           0           0           1           1           0
 3      1           1           1           0           0           1           1
 4      1           1           0           0           1           0           1
 5      0           0           0           0           0           0           0
 6      1           0           1           1           0           1           0
 7      1           1           1           1           0           0           0
 8      1           1           1           0           0           0           0
 9      1           1           1           1           1           1           1
10      0           0           0           0           0           0           0

这些列需要 select 符合特定条件。

我考虑的列数据只是带有“@O13”的列。下面我给出了上面示例中的 selected 列。

BMR_49@O13  BMR_59@O13  BMR_10@O13  
1           0           1       
1           0           1       
1           1           0       
1           0           1       
0           0           0       
0           1           0       
1           1           0       
1           1           0       
1           1           1       
0           0           0   

从 selected 列,我想计算:

1) 所有“1”的总和。在此示例中,我们得到值 16.

2) 包含出现“1”(至少一次)的总行数。从上面的示例中,有 8 行至少包含一次“1”。

最后,

3) 所有“1"s with total lines with occurrence of "1”的总数的比例。

即::(所有“1"s)/(total rows with the occurance of "1”的总和)。 例子 16/8

首先,我尝试使用此命令 select 仅包含“@O13”的列

awk '{for (i=1;i<=NF;i++) if (i~/@O13/); print ""}' $file2

虽然这 运行 但没有显示值。

应该这样做:

awk 'NR==1{for (i=1;i<=NF;i++) if ($i~/@O13/) a[i];next} {f=0;for (i in a) if ($i) {s++;f++};if (f) r++} END {print "number of 1="s"\nrows with 1="r"\nratio="s/r}' file
number of 1=16
rows with 1=8
ratio=2

更具可读性:

awk '
NR==1{
    for (i=1;i<=NF;i++) 
        if ($i~/@O13/)
            a[i]
        next
    }
    {
    f=0
    for (i in a)
        if ($i=="1") {
            s++
            f++
        }
    if (f) r++
    } 
END {
    print   "number of 1="s \
            "\nrows with 1="r \
            "\nratio="s/r
    }
' file