Numpy's float32 and float comparisons Numpy's float32 and float comparisons python-3.x python-3.x

Numpy's float32 and float comparisons


The numbers compare equal because 58682.7578125 can be exactly represented in both 32 and 64 bit floating point. Let's take a close look at the binary representation:

32 bit:  01000111011001010011101011000010sign    :  0exponent:  10001110fraction:  1100101001110101100001064 bit:  0100000011101100101001110101100001000000000000000000000000000000sign    :  0exponent:  10000001110fraction:  1100101001110101100001000000000000000000000000000000

They have the same sign, the same exponent, and the same fraction - the extra bits in the 64 bit representation are filled with zeros.

No matter which way they are cast, they will compare equal. If you try a different number such as 58682.7578124 you will see that the representations differ at the binary level; 32 bit looses more precision and they won't compare equal.

(It's also easy to see in the binary representation that a float32 can be upcast to a float64 without any loss of information. That is what numpy is supposed to do before comparing both.)

import numpy as npa = 58682.7578125f32 = np.float32(a)f64 = np.float64(a)u32 = np.array(a, dtype=np.float32).view(dtype=np.uint32)u64 = np.array(a, dtype=np.float64).view(dtype=np.uint64)b32 = bin(u32)[2:]b32 = '0' * (32-len(b32)) + b32  # add leading 0sprint('32 bit: ', b32)print('sign    : ', b32[0])print('exponent: ', b32[1:9])print('fraction: ', b32[9:])print()b64 = bin(u64)[2:]b64 = '0' * (64-len(b64)) + b64  # add leading 0sprint('64 bit: ', b64)print('sign    : ', b64[0])print('exponent: ', b64[1:12])print('fraction: ', b64[12:])


The same value is stored internally, only it doesn't show all digits with a print

Try:

 print "%0.8f" % float_32

See related Printing numpy.float64 with full precision


The decimal 58682.7578125 is the exact fraction (7511393/128).

The denominator is a power of 2 (2**7), and the numerator span 23 bits. So this decimal value can be represented exactly both in float32 (which has 24 bits significand) and float64.

Thus the answer of Victor T is correct: in internal representation, it's the same value.

The fact that equality answer true for same value, even for different types is a good thing IMO, what do you expect of (2 == 2.0)?