-4

I have a button that, when I press it I want it to update a label (which starts at 0.0) to + 0.1

I get the following:

0.1
0.2
0.30000000000000004
0.4
0.5
0.6
0.79999999999999999
0.89999999999999999
0.99999999999999999
1.09999999999999999

The code I have is:

  double Number = Double.parseDouble(txtNumber.getText());
  double Generator = 0.1;
  Number = (Number + Generator);
  txtNumber.setText(Number + "");

I understand that the way computers work with numbers are not exactly 0.3 but more like 0.2999999... I just wanted a way to round the number so I can easily add 0.1(to)0.9 together without a mass of decimal places.

I have tried adding

Math.round((Number + Generator) * 100) / 100;

although it rounds it downwards to 0 so the label doesn't update.

Andrew Thompson
  • 168,117
  • 40
  • 217
  • 433
JakeB
  • 57
  • 1
  • 7
  • 1
    Use `String.format` to generate the String version of the number. – Hot Licks Mar 27 '14 at 01:46
  • 1
    (BTW, most Java coding standards mimic C standards and use leading lower-case letters for variable names, reserving Upper-Case for class names.) – Hot Licks Mar 27 '14 at 01:50
  • See [What Every Computer Scientist Should Know About Floating-Point Arithmetic](http://docs.oracle.com/cd/E19957-01/806-3568/ncg_goldberg.html).. (and hundreds of duplicates around SO). – Andrew Thompson Mar 27 '14 at 07:14

3 Answers3

4
String myNumberString = String.format("%1.1d", Double.valueOf(myNumber));
Hot Licks
  • 47,103
  • 17
  • 93
  • 151
4

If you want exact decimal addition, you need to use BigDecimal in place of double.

BigDecimal number = new BigDecimal(txtNumber.getText());
BigDecimal generator = new BigDecimal("0.1"); // The "" marks are important
number = number.add(generator);
txtNumber.setText(number.toString());
Dawood ibn Kareem
  • 77,785
  • 15
  • 98
  • 110
1

Some decimals simply can't be represented by a float or double in such way the the difference is small enough. Simply because a computer uses the binary number system. For instance a computer will always fail to represent 1/3rd.

You can use a format, to round the number to one decimal using the following code:

double value = 0.3d;
String.format("%1.1d",value);
Willem Van Onsem
  • 443,496
  • 30
  • 428
  • 555
  • Actually, the problem is with the addition, not the internal representation. It is possible to represent `0.3` with a `double`, then print that `double` and see `0.3`. The problem is that it's not the same `double` that you get from adding `0.1` to `0.2`. – Dawood ibn Kareem Mar 27 '14 at 02:18
  • If I recall IEEE745 correctly, adding two numbers with the same exponent, will always be the correct addition. The problem however is that neither `0.1` neither `0.2` can be reprented correctly. – Willem Van Onsem Mar 27 '14 at 13:05