Vector normalisation

In AWK

For 3 individual vectors of the form:

-2.772  -9.341  -2.857
-5.140  -6.597  -1.823
-2.730  -5.615   1.159

I would like to write a script that parses line by line to (i) normalise, (ii) divide by the norm for *each* vector.

I.e.

sqrt(-2.772^2 + -9.341^2 + -2.857^2)=10.154

-2.772/10.154 = -0.273, -9.341/10.154 = -0.919, -2.857/10.154 = -0.281
[/tmp] awk '{nm=sqrt(($1*$1)+($2*$2)+($3*$3)); print $1/nm FS $2/nm FS $3/nm}' file
-0.273 -0.919946 -0.281371
-0.600509 -0.770732 -0.212982
-0.429911 -0.884231 0.182515

Why does the BEGIN/END commands in this script change the function of the script to loop over all records before doing the division by the norm?

awk 'BEGIN{s=0}{s = s + $1^2 + $2^2 + $3^2}END{print sqrt(s)}' file`

Statements in BEGIN block will be executed before reading any line of file and statements in END block will be executed after all the lines in file are read.

So, initially 's' is set to 0. And $1^2 + $2^2 + $3^2 of each line is added to 's' iteratively. After all the lines are read, sqrt(s) is printed.

General case:

awk '{normp=0;for(i=1;i<=NF;i++)normp+=$i*$i; for(i=1;i<=NF;i++)printf "%8.3f",$i/sqrt(normp);print ""}' infile