0

I'll keep it short. I've got this basic java code:

int listLength = sc.nextInt();
double[] list = new double[listLength];

for(int i = 0; i < list.length; i++){
   list[i] = sc.nextDouble();
}

When I input 1 12345678901234567 Now if I execute this line: System.out.println(list[0] == 12345678901234568.0 && list[0] == 12345678901234567.0);

The console will print: true

If I just print list[0], it prints 12345678901234568

I ask the console to print if a double value is 2 different numbers and it says it's true. How is this possible?

Bas Nijhof
  • 25
  • 2
  • 2
    Numbers in computer hardware have a finite number of bits. For floating-point numbers, this translates into a fixed precision. For Java **double** this is 15 decimal digits. – user16632363 Sep 16 '21 at 00:16
  • 2
    Those aren't two values; they are the same value. `12345678901234568.0 == 12345678901234567.0` is `true` - you can confirm for yourself. – kaya3 Sep 16 '21 at 00:24
  • 2
    See [Is floating point math broken?](https://stackoverflow.com/questions/588004). – Stephen C Sep 16 '21 at 00:49
  • `12345678901234568` in binary is `101011110111000101010001011101011010110100101110001000`, which has three zero bits at the RHS, so it only uses 53 bits when normalized. `12345678901234567` in binary is `101011110111000101010001011101011010110100101110000111`, which needs the three extra bits, and they are not available. – user207421 Sep 16 '21 at 03:51

2 Answers2

3

The Java double-precision float can store between 15-16 digits before the decimal point in the number because that's what the IEEE 754 floating-point standard allows for the maximum integer part. Your number is 17 digits. Try the same test after rounding/truncating a few digits off and it should work as expected.

Juicestus
  • 442
  • 1
  • 7
  • 14
0

Not all numbers can be represented exactly with a double, because there are infinitely many numbers, and only finitely many double values. If you try to store a number in a double, and there's no double value that represents it exactly, you'll get the nearest (or nearest equal) value that can be represented.

In your particular case, 12345678901234567 can't be represented exactly with a double, so whenever you write 12345678901234567.0, the double that's actually stored is the nearest (or nearest equal) available one, which is the one representing 12345678901234568.

Dawood ibn Kareem
  • 77,785
  • 15
  • 98
  • 110