This week's book giveaway is in the Cloud/Virtualization forum.
We're giving away four copies of Mastering Corda: Blockchain for Java Developers and have Jamiel Sheikh on-line!
See this thread for details.
Win a copy of Mastering Corda: Blockchain for Java Developers this week in the Cloud/Virtualization forum!
  • 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 all forums
this forum made possible by our volunteer staff, including ...
Marshals:
  • Campbell Ritchie
  • Paul Clapham
  • Ron McLeod
  • Bear Bibeault
  • Liutauras Vilda
Sheriffs:
  • Jeanne Boyarsky
  • Tim Cooke
  • Junilu Lacar
Saloon Keepers:
  • Tim Moores
  • Tim Holloway
  • Stephan van Hulst
  • Jj Roberts
  • Carey Brown
Bartenders:
  • salvin francis
  • Frits Walraven
  • Piet Souris

Float.valueOf is rounding 999999.99 to 1000000.00

 
Ranch Hand
Posts: 81
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
I'm trying to convert the string "999999.99" to a float, but Float.valueOf( s ) is rounding up to 1000000.00.
Here's what the API says:
...it is regarded as representing an exact decimal value in the usual "computerized scientific notation"; this exact decimal value is then conceptually converted to an "infinitely precise" binary value that is then rounded to type float by the usual round-to-nearest rule of IEEE 754 floating-point arithmetic.

Does anyone know a work-around to prevent the rounding?

[This message has been edited by Bob Graffagnino (edited November 07, 2001).]
 
"The Hood"
Posts: 8521
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Grrrr. . . how frustrating . . . .
not Float.parseFloat()
not (float)Double.parseDouble()
not . . .
 
Bob Graffagnino
Ranch Hand
Posts: 81
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Go Cindy, go Cindy......
 
Wanderer
Posts: 18671
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
A float is not precise enough to represent 999999.99 - ever. It has nothing to do with the valueOf() method - try running the following:
<pre>
float f = 999999.99f;
System.out.println(f);
</pre>
A float is generally subject to roundoffs in its 8th significant digit - in this case, the roundoff goes upward to 1000000.0. The easiest way to avoid this is to use a double or BigDecimal instead. A double will generally have no roundoff until the 18 significant digit, and a BigDecimal will have none unless you tell it to round off - but BigDecimal is notably slower, so there's a tradeoff. I usually just use double for any floating-point value, unless there's a compelling reason to do otherwise.
 
Ranch Hand
Posts: 2823
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Just be aware if the double gets large enough you need to use a formatter or get something like 9.99999999E8.
 
Cindy Glass
"The Hood"
Posts: 8521
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
But getting it INTO the double from the String causes the rounding - so how to fix that?
 
Ranch Hand
Posts: 53
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator

Originally posted by Cindy Glass:
But getting it INTO the double from the String causes the rounding - so how to fix that?


How about:
Double.valueOf(stringVar);
 
Cindy Glass
"The Hood"
Posts: 8521
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
If you read the API for Double.valueOf() it says


this exact decimal value is then conceptually converted to an "infinitely precise" binary value that is then rounded to type double by the usual round-to-nearest rule of IEEE 754 floating-point arithmetic.



Double d = Double.valueOf("999999.99");
System.out.println(d);
float f = d.floatValue();
System.out.println(f);
gets you
999999.99
1000000.00

[This message has been edited by Cindy Glass (edited November 07, 2001).]
 
Ranch Hand
Posts: 88
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
It might be worth remembering that (and ignoring "cup-size" for a moment) that when it comes to the fractional part of a number then binary can only be exact with multiples of half, quarter, eighths, sixteenths, 1/32 etc. So what seems like a simple decimal number 0.1 may actually be an infinite decimal number 0.00011001100110011001100110... in binary.
"cup-size" only makes inaccuracies more inevitable.
 
Jim Yingst
Wanderer
Posts: 18671
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Elaborating on that - there is more than one way to represent floating-point numbers in binary, and some formats do allow all decimal values to be represented exactly. E.g. if 0.1 is treated as 1 * (10 ^ -1) then the mantissa and exponent can both be represented exactly. Something like this is what the JLS means by the "infinitely precise" passage Cindy quotes. However, this is not the way values are stored for int or double types, so roundoff must eventually occur at some point in order so use these data types. Why doesn't Java use an "infinitely precise" form instead? Performance, I suspect.
 
Switching from electric heat to a rocket mass heater reduces your carbon footprint as much as parking 7 cars. Tiny ad:
Building a Better World in your Backyard by Paul Wheaton and Shawn Klassen-Koop
https://coderanch.com/wiki/718759/books/Building-World-Backyard-Paul-Wheaton
reply
    Bookmark Topic Watch Topic
  • New Topic