Hacker News new | ask | show | jobs
by sillysaurus3 4331 days ago
A double can store every integer from -2^53 to 2^53, which seems sufficient to do financial work.

2^53 is 9,007,199,254,740,992

If you want to denote that the last three digits are for fractional dollars (i.e. each integer represents 1/10th of a penny) then you can store any monetary value from -$9 trillion to $9 trillion.

EDIT: Note that it's tempting to think that you can skip converting decimal currency to integer as long as you only use <= 3 digits after the decimal and you're storing values of less than 9 trillion, i.e. it's tempting to think you're safe storing a value like $1,283.212 directly in a double without converting to integer. But I'm pretty sure that's mistaken. You always need to convert to integer so that you're storing 1,283,282 in a double, not $1,283.212

The reason is because certain decimal values which can be represented in base 10 can't be represented in base 2. For example, $0.1 can't be stored into a double as-is; if you try to store 0.1 into a double, you'll get:

  0.1000000000000000055511...
which is where the inaccuracies can start to come into play. Whereas if you convert $0.1 to integer, you'll be storing the value 100 into a double, which comes out to exactly 100 without any error.

Of course, the error may be so small as to be insignificant, but the point is, I'm absolutely certain that integers between -2^53 and 2^53 can be perfectly represented by doubles, but I'm not certain that <= 3 digits of decimal precision can always be accurately represented by doubles for values of less than 9 trillion.

EDIT2: You have to be careful when converting between currencies, too. For example, right now $2 = 204 yen. If you're storing yen, 2^53 yen is different from 2^53 one-tenth-pennies, so the max value that you can store is specific to each currency. This seems like potentially a tricky problem, and may be what the parent commenter was referring to when saying doubles aren't so good for financial work. Still, though, 2^53 integers of precision may be sufficient regardless of which currency you're using.

1 comments

You're right, that's why some languages have built in data types that take care of this issue for you (i.e. decimal in C# or BigDecimal in Java)[1].

[1] http://stackoverflow.com/questions/3730019/why-not-use-doubl...