user3389597
user3389597

Reputation: 471

subtract column from another column in a file and replace the column by subtracted result

Among thousands of files, for example I have a file say 'corr0.txt' like:

1 1 1 1 1 1 2.559346e-08 2.080054e-10
1 1 1 1 1 2 1.398551e-09 2.709745e-09
1 1 1 1 1 3 -7.939651e-10 -1.560374e-09
1 1 1 1 1 4 -4.734811e-09 -1.031029e-09
1 1 1 1 1 5 -7.906407e-10 -1.264427e-09
1 1 1 1 1 6 1.143652e-09 -1.662138e-09
1 1 1 1 1 7 -1.843946e-09 -2.157429e-09
1 1 1 1 1 8 -5.101709e-11 -3.662005e-10

Now I have another file "avg.txt" which is like:

2.13819e-08
-3.29974e-10
-9.25384e-10
-2.3519e-10
-9.54804e-10
-6.87923e-10
2.34904e-10
1.25694e-10

To subtract the column of 'avg.txt' from the 7th column of 'corr0.txt', I write awk command:

awk 'FNR==NR {arr[NR]=$1; next} { print $7-arr[FNR]}'  avg.txt corr0.txt

Now if I want to replace the 7th column of the 'corr0.txt' file with the subtracted result and write the output in a file, how should I modify the command? Thanks for your help.

Upvotes: 3

Views: 543

Answers (2)

Thor
Thor

Reputation: 47099

You can simplify the task if you append the column you want to subtract with paste:

paste corr0.txt avg.txt | awk '{ $7 -= $9; NF-- } 1'

Output if piped to column -t:

1  1  1  1  1  1  4.21156e-09   2.080054e-10
1  1  1  1  1  2  1.72853e-09   2.709745e-09
1  1  1  1  1  3  1.31419e-10   -1.560374e-09
1  1  1  1  1  4  -4.49962e-09  -1.031029e-09
1  1  1  1  1  5  1.64163e-10   -1.264427e-09
1  1  1  1  1  6  1.83158e-09   -1.662138e-09
1  1  1  1  1  7  -2.07885e-09  -2.157429e-09
1  1  1  1  1  8  -1.76711e-10  -3.662005e-10

Explanation:

The column to subtract is the 9th column, so assigning the subtraction to $7 is sufficient. NF-- removes the now redundant 9th column. The 1 at the end invokes the default implicit code block: { print $0 }.

Code golf note

If you know that there are no empty lines in the data file the awk-script can be shortened by exploiting the fact that --NF will always evaluate to true:

paste corr0.txt avg.txt | awk '{$7-=$9}--NF'

Upvotes: 1

Chris Seymour
Chris Seymour

Reputation: 85775

Just reassign to $7and print the whole line:

$ awk 'FNR==NR{a[NR]=$1;next}{$7=$7-a[FNR];print}' avg.txt corr0.txt

Upvotes: 3

Related Questions