Why casting from int to float around a value?

I read CS: APP, and with regard to drops, he says that when casting from int to float, the number cannot overflow, but it can be rounded.

It seemed strange to me because I did not know what to twist, so I tried it. I thought this would only be true for very large integers (near INT_MAX / INT_MIN ), but rounding occurs with values ​​of about one hundred million. (Do not know where exactly this happens in the first place).

Why is this happening? The float range is much larger than the int range. We can say that floating point numbers cannot be represented exactly, but there are no changes in the value when converting from int to double . The advantage of double over float is that it has a greater range and accuracy. But the float still has enough range to β€œencapsulate” integers, and the accuracy shouldn't matter much, since integers don't have decimals (well, all 0), or am I not mistaken?

Here is some output I got (here is the code: http://pastebin.com/K3E3A6Ni ):

 FLT_MAX = 340282346638528859811704183484516925440.000000 INT_MAX = 2147483647 (float)INT_MAX = 2147483648.000000 (double)INT_MAX = 2147483647.000000 INT_MIN = -2147483648 (float)INT_MIN = -2147483648.000000 ====other values close to INT_MIN INT_MAX==== INT_MAX-1 = 2147483646 (float)INT_MAX-1 = 2147483648.000000 INT_MIN+1 = -2147483647 (float)INT_MIN+1 = -2147483648.000000 INT_MAX-2 = 2147483645 (float)INT_MAX-2 = 2147483648.000000 INT_MAX-10 = 2147483637 (float)INT_MAX-10 = 2147483648.000000 INT_MAX-100 = 2147483547 (float)INT_MAX-100 = 2147483520.000000 INT_MAX-1000 = 2147482647 (float)INT_MAX-1000 = 2147482624.000000 (float)1.234.567.809 = 1234567808.000000 (float)1.234.567.800 = 1234567808.000000 (float)1.000.000.005 = 1000000000.000000 (float)800.000.003 = 800000000.000000 (float)500.000.007 = 500000000.000000 (float)100.000.009 = 100000008.000000 
+6
source share
2 answers

I assume that by float you mean a 32-bit binary value of an IEEE-754 floating point, by double you mean a 64-bit binary value of an IEEE-754 floating point, and by int you mean a 32-bit integer.

Why is this happening? The float range far exceeds the int range.

Yes, but the precision of the float is only 7-9 decimal digits. To be more specific, the value is only 24 bits wide ... so if you try to store 32 bits of information there, you will have problems.

but when converting from int to double there is no change in value

Of course, since double has a 53-bit value - enough space for a 32-bit integer!

To think of it differently, the gap between consecutive int values ​​is always 1 ... whereas the gap between consecutive float values ​​starts very, very small ... but increases as the value increases, it reaches "more than 2", until you reach the limit of int ... so you get on a scene where not every int can be accurately represented.

To think of it differently, you can simply use the principle of pigeon-holes ... even ignoring the NaN values, there can be no more than 2 32 float , and at least one of them is not an exact int value - take 0, 5, for example. There are 2 values ​​of 32 int , so at least one int value does not have an exact representation of float .

+9
source

A typical float , which is implemented with the 32-bit IEEE-754 representation, has only 24 bits for the value, which allows about 7 decimal digits of precision. This way you will see rounding as soon as you hit millions (2 24 & approx; 16M).

(With a double value is 53 bits and 2 53 & approx; 9 * 10 15. )

+7
source

Source: https://habr.com/ru/post/981990/


All Articles