5 ms·
People might not care about more than 7 digits of Pi, but they sure care about the first significant digit of 0.1+0.2 not being "2". Also I don't think it woul
by KeplerBoy 3y ago
People might not care about more than 7 digits of Pi, but they sure care about the first significant digit of 0.1+0.2 not being "2".
Also I don't think it would matter if a language like Python would switch to BigDecimals as the default option. Python does such a ridiculous large amount of stuff unrelated to the actual math, that bit of lost performance won't break the camel's back.
- bla3 3y agoThe first significant digit of "0.1" and "0.2" _is_ 3! The first significant digit of "0.3" just isn't 3. In case anyone hasn't seen it yet, if you print a double with enough fractional values, you'll eventually get its "true" value (because 2 divides 10). >>> print('%.60f' % 0.1) 0.100000000000000005551115123125782702118158340454101562500000 It's only zeros after these zeros. Here are the "true" values of 0.2, 0.3, and their sum: >>> print('%.60f' % 0.2) 0.200000000000000011102230246251565404236316680908203125000000 >>> print('%.60f' % 0.3) 0.299999999999999988897769753748434595763683319091796875000000 >>> print('%.60f' % (0.1 + 0.2)) 0.300000000000000044408920985006261616945266723632812500000000 Turns out 0.1 + 0.2 is actually the number right after "0.3": >>> print('%.60f' % math.nextafter(0.3, 100)) 0.300000000000000044408920985006261616945266723632812500000000 If you don't use a ton of decimal digits, by default the runtime prints the shortest decimal number that has the same binary representation as the true value when converting that decimal number to binary. Much of the confusion around floats is due to that convenience feature that aims to make floats less confusing.
- eru 3y ago> If you don't use a ton of decimal digits, by default the runtime prints the shortest decimal number that has the same binary representation as the true value when converting that decimal number to binary. The algorithm to do this efficiently is quite interesting, too.
- bee_rider 3y agoI don’t think people do (or should) actually care about the internal representation of the first digit of .1 + .2. They might care about the printed representation. If you round to the nearest, like, 10E-8 (maybe relative if your numbers being printed have massive range) it should be basically fine with doubles.
- Gordonjcp 3y agoCan you give an example of why you think the first significant digit of "0.1+0.2" is 2? Unless you're displaying an unreasonable number of places to the right of the point, it's 3. Nothing - *nothing* - needs more than about four or five significant digits.
- bazoom42 3y ago> Nothing - nothing - needs more than about four or five significant digits. So if you have a million in the bank, you would be fine with a 100$ rounding error on each transaction?
- Gordonjcp 3y agoYou don't use floats for money, because it's an integer.
- taeric 3y agoOddly, money is not an integer at large scales. At least, if you meant to calculate it in pennies, that doesn't work. Consider, what is the cost of gas?
- sweetjuly 3y agoI'm not quite sure what you mean? In most any case I can imagine, uint64 is quite enough to count money in pennies, assuming inflation doesn't get truly out of hand.
- taeric 3y agoGas is priced in sub penny values. Similarly, returns and other values are all typically calculated in sub penny values. You could store in 1/100th of a penny, I suppose? I'm not entirely sure that will work out for all calculations.
- Gordonjcp 3y ago
- nyrikki 3y agoDecimal types made it into the c/cpp standards this year, hopefully this will mean that more than Power and Japanese Sparc chips may have radix 10 support soon. One of the nice things is that it will be faster than the arbitrary precision libs and the sum of any two numbers will be representable. But arbitrary precision libraries are incredibly slow. Compared to radix 2 floats. Note that it won't ever be the default, as the standard imprecise but deterministic floats are an important feature for floats. Even with a piece of paper of arbitrary length, the real numbers are uncomputable almost everywhere and even if they weren't you still need to keep things in the countable infinity sets to be semi-decidable. We will see if decimal types, which require 4 bits for the radix become more common now that c/cpp support them but that may be optimistic.
- lsllc 3y ago> Decimal types made it into the c/cpp standards this year Are you referring to TR 24732 (at least for C)? Is that going to be in C23?
- nyrikki 3y agoProbably safest to point you to here for C23 but TS 18661-2:2015 TR 24732 was withdrawn. https://en.cppreference.com/w/c/23 https://en.cppreference.com/w/c/23 Note the link to paper n2341 https://open-std.org/JTC1/SC22/WG14/www/docs/n2341.pdf https://open-std.org/JTC1/SC22/WG14/www/docs/n2341.pdf C++ is going to be a library for now I think, but haven't looked recently.
- lsllc 3y agoThank you :-)