Originally posted by Hanna Habashy:
...Why the floating point in a BigDecimal number is not accurate? ...
It's because the primitive double you passed to the BigDecimal constructor cannot be stored accurately. See the API documentation for BigDecimal(double val), which will describe the problem and the solution.
Why the floating point in a BigDecimal number is not accurate?
BigDecimal num = new BigDecimal(2.001);
I think that this was a good question. I've known about base-conversion and rounding errors, but I thought that I read that everything would be precise if you only used BigDecimal instead of the primitive double.
I think that I might just stick with using primitive doubles and use my functions to compare them instead of using Java's relational operators. My comparison methods count doubles that are very close as being equal.
Since BigDecimal isn't always accurate either, I might just as well use doubles.
[ May 23, 2007: Message edited by: Kaydell Leavitt ]
I'm not sure where a statement like that might be found. BigDecimal is generally more accurate. But still some values fundamentally cannot be stored in decimal form without infinite memory, e.g. 1.0/3.0 = 0.33333... This is why BigDecimal's divide() method is overloaded with versions encouraging you to specify the scale of the answer. Decimal division is inherently prone to require roundoff at some point, and so the recurring question is, how precise do you want it?
In the case Hanna showed, the inaccuracy really comes from the primitive double that was used in the BigDouble constructor. BigDouble's toString() is simply giving a more precise string representation of the inaccurate value that 2.001 represents. If you want a BigDecimal that really means exactly 2.001, use one of the other constructors, e.g. using String:
everything would be precise if you only used BigDecimal instead of the primitive double.
in the example in the original post, they did NOT only use BigDecimals. that 2.001 is considered a double. this is inherently not accurate. The value must be rounded to a value that a double CAN hold, and it is this inaccuracte value that gets passed into BigDecimal.