# Calculating percentages in arbitrary number of columns

Given this sample input:

ID     Sample1     Sample2      Sample3
One      10          0            5
Two      3           6            8
Three    3           4            7


I needed to produce this output using GNU AWK (awk in Linux, gawk in BSD):

ID    Sample1 Sample2 Sample3
One   62.50   0.00    25.00
Two   18.75   60.00   40.00
Three 18.75   40.00   35.00


This is how I solved it:

function percent(value, total) {
return sprintf("%.2f", 100 * value / total)
}
{
label[NR] = $1 for (i = 2; i <= NF; ++i) { sum[i] += col[i][NR] =$i
}
}
END {
title = label[1]
for (i = 2; i <= length(col) + 1; ++i) {
title = title "\t" col[i][1]
}
print title
for (j = 2; j <= NR; ++j) {
line = label[j]
for (i = 2; i <= length(col) + 1; ++i) {
line = line "\t" percent(col[i][j], sum[i])
}
print line
}
}


NR==1 {print; next}
label[NR] = $1 for (i=2; i<=NF; i++) { sum[i] +=$i; val[NR,i] = $i } } END { OFS = "\t" for (nr=2; nr<=NR; nr++) {$1 = label[nr]
for (i=2; i<=NF; i++) $i = sprintf("%.2f", 100*val[nr,i]/sum[i]) print } }  • don't need to store the header line, just print it and move on • I find sum[i] += col[i][NR] =$i needlessly complicated