jxie0755
jxie0755

Reputation: 1742

Why does Math#nextUp not increment by Double.MIN_VALUE?

I learned this from the Java documentation

It basically says that:

Returns the floating-point value adjacent to d in the direction of positive infinity.

and especially:

If the argument is zero, the result is Double.MIN_VALUE

With this logic:

Math.nextUp(double x) - x should always be Double.MIN_VALUE.

So I tested it out:

double d_up = Math.nextUp(0);
System.out.println(d_up);                        // 1.401298464324817E-45
System.out.println(d_up == Double.MIN_VALUE);    // false
System.out.println(Double.MIN_VALUE);            // 4.9E-324

and it doesn't even work with zero.

Why does Math.nextUp(double x) not equal x + Double.MIN_VALUE?

Upvotes: 0

Views: 152

Answers (2)

Eric Postpischil
Eric Postpischil

Reputation: 223702

The floating-point numbers are similar to this: 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 20, 30, 40, 50, 60, 70, 80, 90, 100, 200, 300, 400, 500,…

“Adjacent” means two numbers are next to each other in this list. For numbers in this list, Math.nextup(x) - x may produce 1, 10, or 100, depending on where in the list x is.

Upvotes: 2

Óscar López
Óscar López

Reputation: 236124

Try this:

double d_up = Math.nextUp(0d); // see the little `d` there :)

Or this, it works as well:

double d_up = Math.nextUp(0.0); // `0.0` is a `double` literal

You need to pass a double for the advertised contract to work. Now your test works!

4.9E-324
true
4.9E-324

Just to be clear, you were passing a float before, so this was the method that got executed:

public static float nextUp​(float f)

... And naturally, that one returns Float.MIN_VALUE when 0 (an int) is passed as a parameter, because it gets automatically casted to a float. Bottom line: mind your types, make sure to cast to the right one.

Regarding the last part of your question, there's no reason why this equation should work: Math.nextUp(x) - x == Double.MIN_VALUE. double numbers are not evenly spaced, the "distance" between any two numbers is not necessarily Double.MIN_VALUE.

This is related to the fact that decimal values in a computer cannot be represented exactly, it's all an approximation that depends on the number of bits used to represent them, and that's a finite quantity - and between any two real numbers there's an infinite number of reals.

Upvotes: 4

Related Questions