For gawk
you need to specify you want to use the bignum package (if gawk
was compiled with a link to that package):
$ gawk -M 'BEGIN{print 1455594303469326836 - 1455594303468741117}'
585719
(You can also do gawk --bignum 'prog'
for the same function as gawk -M
)
Without the -M
switch, you can see the overflow take place by converting the input to integers by adding 0
to the string. Note the second column is not the same as the first:
$ echo "1455594303469326836 1455594303468741117" | awk '{print $1 " => " $1+0,ORS $2 " => " $2+0}'
1455594303469326836 => 1455594303469326848
1455594303468741117 => 1455594303468741120
vs
$ echo "1455594303469326836 1455594303468741117" | awk -M '{print $1 " => " $1+0,ORS $2 " => " $2+0}'
1455594303469326836 => 1455594303469326836
1455594303468741117 => 1455594303468741117
Since IEEE 754 doubles have 53 bits of precision for the mantissa (usable for an exact integer representation up to that size) they start to loose exact representation ability for an integer with more than 53 bits of size:
$ awk 'BEGIN{print 2**53, 2**53+1}'
9007199254740992 9007199254740992
^ ^ not +1 in least significant digit
$ awk -M 'BEGIN{print 2**53, 2**53+1}'
9007199254740992 9007199254740993
^ ^ fixed...
Your input requires 61 bits to represent exactly (or 62 bits with the sign bit), so you loose the ability to represent the least significant digits of the input.
Options
If you do not have gawk
with the bignum option, you can use perl
with BigNum:
$ perl -Mbignum -E 'say 1455594303469326836 - 1455594303468741117'
585719
python:
$ python -c 'print 1455594303469326836 - 1455594303468741117'
585719
bc:
$ echo "1455594303469326836 - 1455594303468741117" | bc
585719
ruby:
$ ruby -e "puts 1455594303469326836 - 1455594303468741117"
585719
But basic POSIX awk -- no bueno for arbitrarily precision integer or non IEEE 754 floating point math. All arithmetic in POSIX awk (or gawk without bignum) is done with IEEE double precision which overflows with the size input you have.