• Post Reply Bookmark Topic Watch Topic
  • New Topic
programming forums Java Mobile Certification Databases Caching Books Engineering Micro Controllers OS Languages Paradigms IDEs Build Tools Frameworks Application Servers Open Source This Site Careers Other Pie Elite all forums
this forum made possible by our volunteer staff, including ...
Marshals:
  • Campbell Ritchie
  • Liutauras Vilda
  • Tim Cooke
  • Jeanne Boyarsky
  • Paul Clapham
Sheriffs:
  • Devaka Cooray
  • Ron McLeod
  • paul wheaton
Saloon Keepers:
  • Tim Moores
  • Piet Souris
  • Tim Holloway
  • Stephan van Hulst
  • Carey Brown
Bartenders:
  • Al Hobbs
  • Frits Walraven
  • Scott Selikoff

Issue adding double value

 
Greenhorn
Posts: 20
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Printing out as
d1 + d2 : 2098700.0300000003
while I expect 2098700.03, can anyone explain the reason?
 
Bartender
Posts: 4568
9
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Floating point variables aren't very good at storing exact values. Remember that the number is stored internally in binary, and 2095475.03 won't be represented exactly in binary.

So you've got two options.

- If you need the calculations to be exact, then look at using the BigDecimal class to represent numbers and do calculations.

- If you don't care about these tiny inaccuracies, but all you care about is getting sensible output, do the calculations as you are, and try the DecimalFormat class to produce output to the accuracy you want.
 
Bartender
Posts: 2700
IntelliJ IDE Opera
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
That is how floating point calculations work. It basically is because not every number can be stored in a double so it will take the closed value. If you want it to have a certain format then you can use NumberFormat.
 
Java Cowboy
Posts: 16084
88
Android Scala IntelliJ IDE Spring Java
  • Likes 2
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
See also question #20 in our FAQ.
 
Mary Joe
Greenhorn
Posts: 20
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Thanks what I was trying to do was importing a file.

The header had a total which was giving the value 2098700.03
which will be compared against the total of the relevant filed(of Numeric(5,2)) which is a double in the body
which can be from upto a total of 50000 rows.
This total also represented as a double was returning as 2098700.0300000003 and hence it was throwing an error beacuse the values didn't match.
I will try using BigDecimal

Any example you have on addition on BigDecimal
 
Greenhorn
Posts: 4
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
BigDecimal bd1= new BigDecimal("2095475.03");
BigDecimal bd2 = new BigDecimal("3225.0");
bd1.add(bd2);
System.out.println("BIG DECI " + bd1);


This will print the result you want
 
Mary Joe
Greenhorn
Posts: 20
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
What I didn't understand though was the same logic was used to calculate the header total as well, which didn't present with the same issue.

total += row.getFee().doubleValue();
 
Bartender
Posts: 10780
71
Hibernate Eclipse IDE Ubuntu
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Mary Joe wrote:Printing out as
d1 + d2 : 2098700.0300000003
while I expect 2098700.03, can anyone explain the reason?


Unfortunately, the original Goldberg page seems to have disappeared, but this one looks similar. If you really need fixed decimal values, you're usually better off using BigDecimal than double.
 
lowercase baba
Posts: 13081
67
Chrome Java Linux
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Comparing floating point numbers for equality is ALWAYS risky in any computer language. if you have to do so, you generally figure out some delta that the difference should be less than...i.e.:



And even this is dangerous if the magnitude of your numbers can vary.
 
Mary Joe
Greenhorn
Posts: 20
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
I have overcome the issue firt mentioned in my post using BigDecimal.

Now I have a different one.


Bigdecimal one = 2948.0
Bigdecimal one = 2948 (this is being returned from a jdbc query of Double value new BigDecimal(resultRow.getFee().toString());)
Again failing on comparison, anway to impose the decimal ?
 
Greenhorn
Posts: 27
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
I do believe your BigDecimal object has its current scale set to Zero.

The scale defines the number of decimal places the object will hold.

Take a look at the various setScale() Methods in the API, you can also define the scale in several constructors.

Java BigDecimal

Also I would suggest when setting scale you also define the rounding mode. BigDecimal.ROUND_HALF_UP is the standard rounding we all should know from school.

 
Mary Joe
Greenhorn
Posts: 20
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Thanks Joshua that helped a lot.

All issues resolved
 
With a little knowledge, a cast iron skillet is non-stick and lasts a lifetime.
reply
    Bookmark Topic Watch Topic
  • New Topic