Live data from Hacker News

Using floating-point numbers for money

evanjones.ca

91–100 of 128 posts

Re: Using floating-point numbers for money

#92
> 0.1 + 0.2: Produces 0.30000000000000004

No, it doesn't. It produces 0.3000000000000000444089209850062616169452667236328125.

> 1.40 * 165: produces 230.99999999999997

No, it doesn't. It produces 230.999999999999971578290569595992565155029296875.

> round(2.675, 2) produces 2.67

No, it doesn't. It produces 2.6699999999999999289457264239899814128875732421875.

> This is because 2.675 is actually 2.6749999999999998

No, it isn't. For one, 2.675 obviously is not 2.6749999999999998, but it also isn't converted to 2.6749999999999998 to be stored as a floating point number, it is converted to 2.67499999999999982236431605997495353221893310546875.

> round(2.665, 2) which produces 2.67

No, it doesn't. It produces 2.6699999999999999289457264239899814128875732421875.

> However, in floating-point numbers, it is above the halfway point (0.00500000000000000097)

Well, it is above the halfway point, but it's actually 0.0050000000000000009714451465470119728706777095794677734375.

> I am not a theoretician and have not proven that this is actually correct.

So, all the numbers are wrong, you have no clue whether your wrong results generalize, but you use that as the basis for advice to other people? I only can hope that you don't write software for other people to use.

Re: Using floating-point numbers for money

#93
post #5

Sorry, but I remain skeptical. The same people who use `float` for financial calculations are probably the same people who don't understand how/why to do the rounding described to avoid these problems. Way too many programmers think that they are working in base 10 when using float. Why not just make them use it, and keep them out of trouble. Also, I wonder what the overhead of rounding every operation is? Comparable…

This thread seems to be unaware of DEC64, so this seems as good a place as any to point to this: http://www.dec64.com/

The gist: It's efficient (adds and mults in a few instructions), and preserves the decimal representation.

It's quite simple, really: Store a whole-number integer with a smaller one representing the number of shifts to the decimal point. This is probably a good choice for sensitive financial calculations.

Re: Using floating-point numbers for money

#94
>We can solve these problems by rounding after every operation.

In my experience one should do exactly the opposite, round/format only the very last result when you need to print it, otherwise always keep all the decimals in the intermediary results to avoid accumulating rounding errors as in a Superman 3 bank hack (aka "salami slicing"). I did a lot of affiliate and e-commerce software in my time and if you're careful you can use floats (sometimes you have to deal with old systems working that way), but fixed-point calculations with integers are way easier and safer. Just make sure to store enough extra decimal places, not just the 2 that you print and you can calculate interests, exchange currencies, charge 0.5% fee on $0.01 per click transactions, whatever - it works just fine.

Re: Using floating-point numbers for money

#95

> Solution: Round after every operation No, the solution is not to use floating point numbers to store money. I worked on an iOS app in fintech for years, and let me assure you, using floating point numbers to calculate currency is an exercise in frustration and lack of correctness. When balances are wrong you're losing your customers money, which in turn loses trust in your product. You know it's inexact, an approxi…

> Just do it with a fixed-precision decimal number, and represent it as a string.

Why? If you are going to do that, might as well use an integer of cents. It's more compact and if you're worried about these calculations and storing this kind of information, it's likely you are storing lots of it (or it wouldn't be a problem).

Re: Using floating-point numbers for money

#96
post #63

Earlier quoted context omitted.

> I wonder what the overhead of rounding every operation is? Comparable to the cost of using a proper Decimal class? For what it’s worth, for the major ICs (Intel, NVIDIA, etc.) there is zero extra overhead. A choice of rounding modes is part of the floating point operation’s instruction. And keep in mind that a floating point op is always rounding no matter what you do, the question is whether it’s always using the…

> You run out of integer precision at 2^24, which is only 16 million To be fair, the author seems to be suggesting using double-precision floating point. If you use integer numbers of pennies, signed 32-bit integers cap out at a similar value of $21M. 32 bits is just too small for financial calculations.

You’re absolutely right; he did say 64 bit. I just wouldn’t do that blindly either, and the author admitted to not being fluent in error analysis. The issue with even doubles is that the magnitude of your error in a running total calculation is a sum of all the errors of your largest intermediate results (the results of multiplies you don’t see or store explicitly). That means with a bank account, the error of your calculations continues to grow forever unless you are explicitly correcting the errors. Rounding does not solve that, so even using doubles for money is a sketchy proposition unless you really know what you’re doing.

Re: Using floating-point numbers for money

#97

Earlier quoted context omitted.

> That’s in decimal, but since computers use binary Well, if you tell them to, e.g., by using a binary floating point type instead of a decimal type.

No, we aren’t using computers with logic gates that have 10 discrete states. Even if you’re programming to decimal, the underlying representation is still binary. But there are numerical differences between using decimals represented by rationals with binary integer numerators and denominators, vs floating point with binary mantissa and exponent.

> No, we aren’t using computers with logic gates that have 10 discrete states. Even if you’re programming to decimal, the underlying representation is still binary.

That is not the sense of "computers use binary" that justifies the conclusions in the sentence in which the phrase was used in the post being responded to, so while true on its own, in context it is an example of the fallacy of equivocation.

Re: Using floating-point numbers for money

#98
post #82
post #69

Earlier quoted context omitted.

> How are you going to do linear interpolation, let alone exponential growth, without floating-point? Fixed point is one answer, but I see you know that already. I don’t know what the banks use for interest, but I can guarantee that it’s not float32. > If you have some routines for dividing fixed-point numbers, one, why do you believe they have more accuracy than floating point Fixed point routines do not have more b…

> I think asking about correctness is a straw man. The issue is really about safety, predictability, and controllability. Uh, and compliance? (if you didn't mean to imply that under "controllability")

Yeah, definitely. My list certainly isn’t exhaustive; just trying to express that use of floating point isn’t only a matter of correctness, there are lots of other factors. The dev time cost of using floats correctly for financial calculations is higher than the dev time cost of using ints or fixed point numbers.

Re: Using floating-point numbers for money

#99
post #81
post #5

Sorry, but I remain skeptical. The same people who use `float` for financial calculations are probably the same people who don't understand how/why to do the rounding described to avoid these problems. Way too many programmers think that they are working in base 10 when using float. Why not just make them use it, and keep them out of trouble. Also, I wonder what the overhead of rounding every operation is? Comparable…

It's hard to consider float anything, but a hack - and certainly something to keep away from discrete domains (countables). I'm a little more curious on the suitability of using integers for money though (integer number of pennies). I suppose there are cases (and rules) concerning fractional pennies? Like in the case of percents of interests, often given by the year, accumulated[1] by the month? [1] that's probably n…

> It's hard to consider float anything, but a hack

GPU engineers might have something to say about that. Depending on the context, trading off on precision can be a valid engineering choice.

Re: Using floating-point numbers for money

#100
post #71

Earlier quoted context omitted.

> Also, you are going to end up storing in decimal fields in the database anyway. why not use cents as the unit and store it without decimals?

Because it is a massive pain in the butt for your report writers / business intelligence people whose tools expect decimal fields. Never mind all the existing code that expects an actual decimal and not an integer. Plus tax folks like like their mills.

> Because it is a massive pain in the butt for your report writers / business intelligence people whose tools expect decimal fields

That's a matter for the ETL that dumps the data on their screens.

Post reply on HN