34 ms·
edit: The OP has accepted my pull request and this explanation is now directly available on the website. It's a shame that the web page doesn't explain why flo
by such_a_casual 11y ago
edit: The OP has accepted my pull request and this explanation is now directly available on the website.
It's a shame that the web page doesn't explain why floating point numbers are inaccurate when it comes to decimals. It's actually pretty simple. When you have a base 10 system (like ours), it can only express fractions that use a prime factor of the base. The prime factors of 10 are 2 and 5. So 1/2, 1/4, 1/5, 1/8, and 1/10 can all be expressed cleanly because the denominators all use prime factors of 10. In contrast, 1/3, 1/6, and 1/7 are all repeating decimals because their denominators use a prime factor of 3 or 7.
In binary (or base 2), the only prime factor is 2. So you can only express fractions cleanly which only contain 2 as a prime factor. In binary, 1/2, 1/4, 1/8 would all be expressed cleanly as decimals. While, 1/5 or 1/10 would be repeating decimals.
So 0.1 and 0.2 (1/10 and 1/5) while clean decimals in a base 10 system, are repeating decimals in the base 2 system the computer is operating in. When you do math on these repeating decimals, you end up with leftovers which carry over when you convert the computer's base 2 (binary) number into a more human readable base 10 number.
- iamphilrae 11y agoTHANK YOU! That is one of the best explanations on that matter I have seen. I've never considered why floating points are inaccurate, I just took it for a given (which I hate doing). Now I understand why, and so my own wisdom has increased ever so slightly. Today is a good day.
- acqq 11y agoSee also: http://cs.furman.edu/digitaldomain/more/ch6/dec_frac_to_bin.htm http://cs.furman.edu/digitaldomain/more/ch6/dec_frac_to_bin.... ".1 (decimal) = .00011001100110011 . . . (base 2)" Notice the repeating pattern? The exact number must have infinite number of binary digits. Wherever you cut (whichever fixed number of bits you want to keep) you lose something.
- Nemi 11y agoSo, this is a great explanation. I have never heard it expressed this way and I love it. However, I am a little confused. In your first paragraph you say that 10's prime factors are 5 and 2, so 1/10 can be expressed cleanly. In paragraph two you say that binary only has a prime factor of 2, but 10 is divisible by 2, so why doesn't 1/10 express cleanly in binary?
- aeorgnoieang 11y agoA fraction can only be expressed 'cleanly' if its denominator uses only the prime factors of the base.
- btilly 11y agoFor example, 30 is divisible by 10, but 1/30 is not represented cleanly in base 10.
- such_a_casual 11y agoIn the fraction 1/10, the denominator is 10. The prime factors of 10 are 2 and 5. Binary does not contain the prime factor of 5 necessary to represent 1/10 cleanly as a decimal. It only contains the 2. Similarly, the prime factors for 1/6 would be 3 and 2. In a base 10 number system, you only have the 2. So you end up with a repeating decimal (0.1666666).
- StefanKarpinski 11y agoSpot on. I would add to this explanation that the real confusion comes from the fact that in most languages when you write `0.1`, it doesn't mean 0.1 = 1/10 – instead it means the closest number to 0.1 of the form n/2^k where n < 2^53. Namely 0.1000000000000000055511151231257827021181583404541015625, which we can represent in decimal because 2 divides 10. And, of course, the illusion that `0.1` is actually 0.1 is supported by the great efforts [1] made to print floating-point values with the least number of digits necessary to reproduce them, so `0.1` still looks like 0.1 when you print it even though it isn't. [1] http://www.cs.tufts.edu/~nr/cs257/archive/florian-loitsch/printf.pdf http://www.cs.tufts.edu/~nr/cs257/archive/florian-loitsch/pr...
- fryguy 11y agoIn decimal if you only have 5 digits for mantissa and you write 2/3, it becomes 0.66667 which is a little bit more than 2/3. Similarly, if you write the binary number 0.0000'0000'1 in decimal with 5 digits for mantissa, it becomes 0.0039063 instead of 0.00390625. If in some faraway land they use binary math, they would likely ask why such a simple binary number got rounded off.
- benten10 11y agoHuhh, that was a totally unexpected encounter to Prof. Ramsey's page.
- deleted 11y ago[deleted]
- jayceekay 11y ago> In contrast, 1/3, 1/6, and 1/7 are all repeating decimals because their denominators use a prime factor of 3 or 7. doesn't 1/6 use a prime factor of 2 as well?
- thedufer 11y agoYes, but in order to have a non-repeating decimal expansion, the denominator must share _all_ of its factors with the base. That is, only fractions that, when reduced, have a denominator of the form 2^n*5^m (for natural numbers n, m) will terminate in base 10. The explanation given could probably be clearer.
- deleted 11y ago[deleted]
- jayceekay 11y agoah yes, the _all_ is what i missed. thanks.
- such_a_casual 11y agoIn the fraction 1/6, the prime factors of the denominator are 2 and 3. A base 10 number system has the 2 but not the 3.
- jayceekay 11y agogot it, thanks!
- Raphmedia 11y agoTo live in a world where information is not only accessible, but where you can also contribute to it easily is truly amazing. I use Git daily for source control, but I am always amazed when I see it used to manage content in an open source way.
- such_a_casual 11y agoCompletely agree. I would love to see more content creators using things like github to allow others to contribute and improve content.
- david_ar 11y agoObligatory pedantic comment: "base-2 decimal" is an oxymoron https://en.wikipedia.org/wiki/Repeating_decimal#Extension_to_other_bases https://en.wikipedia.org/wiki/Repeating_decimal#Extension_to...
- raiph 11y ago> 0.1 and 0.2 ... are repeating decimals ... Au contraire, `0.1` and `0.2` are non-repeating decimals. Their approximations may be repeating of course, and some languages indulge in such approximations, but there's nothing intrinsic about `0.1` that requires that it be approximated prior to storage rather than stored with 100% accuracy. Many lisps do what it takes to store rationals as rationals, maintaining 100% accuracy. Perl 6 likewise treats literals of the form `1/10` or `0.1` as the rationals they are, again maintaining 100% accuracy.
- reuven 11y agoI have been teaching programming for years, and love to point out that floating-point arithmetic isn't accurate. Many experienced programmers are shocked to discover the problems with floats. But I never before had a good answer for which numbers would be accurate, and which wouldn't. This explanation was crystal clear and helpful. Thanks for providing it.