I am trying to store 49212.619 in float value and don't want to loose any precision.
But it always change to this. I have tried this with different floating point numbers having length of 5 or 6 digits after decimal and similar behaviour is seen.
So I was just wondering despite the Float range being so large from this ideally 3.7 * 10 raise to 37
why is it not able to store these values.
let floatVal: Float = 49212.619
print(floatVal) -> 49212.617
I don't think this is exactly representable, but you can use Double to lose less precision:
let doubleVal: Double = 49212.619
print(doubleVal) // 49212.619
In fact, the value is 49212.618999999999, but that's the closest it can do (the next representable value is 49212.619000000006).
That's just a limitation of floating-point math. If you need decimal math, look at Foundation's
Because the greater the magnitude of a floating point value, the greater the distance between the values (see the
.ulp property of
Float¨s highest (non-infinite) representable value, the distance between representable values is:
Float.greatestFiniteMagnitude.ulp = 2.02824096E+31
And even at such a relatively small magnitude as a million, the distance between each representable value is as large as:
Float(1_000_000).ulp == 0.0625
Also, note that the "Float in Swift" is not using some Swift-specific format, it's the same IEEE 754 standard 32-bit single precision floating point format that most other languages use.
Float has 24 bits of precision, which is approximately 7 decimal digits. Your number has 8 digits, so it is to be expected that when rounded to
Float the last digit or 2 will be off.
Double has 53 bits of precision, which is approximately 16 decimal digits.
Note that what matters is the total number of digits, not where the decimal point is. That’s why these are called “floating-point” numbers: the position of the decimal point is stored separately. (And of course it’s all stored in binary not decimal, which is why such rounding occurs in the first place.)
Thank you for the reply guys.
So the conclusion is if I need more precision either to use double or accept the behaviour.
And, of course, it all depends on what you intend to do with it once you've stored it.
For example, if all you need is to store the value 49212.619, then it is exactly representable as eg the
"49212.619". But you cannot do arithmetic etc with it.