Why does double.IsNegative(double.NaN)
unexpectedly return true
whereas double.NaN < 0
returns false
as expected?
Java Double isNaN() Method The isNaN() method of Java Double class returns true: If the value of this Object is Not-a-Number (NaN). If the argument passed is Not-a-Number (NaN). Otherwise, the method returns false.
Use the IsNaN method to determine whether a value is not a number. The Equality operator considers two NaN values to be unequal to one another. In general, Double operators cannot be used to compare Double. NaN with other Double values, although comparison methods (such as Equals and CompareTo) can.
NaN values are tested for equality by using the == operator, the result is false. So, no matter what value of type double is compared with double. NaN, the result is always false.
What you can do is use compare / compareTo: Double.NaN is considered by this method to be equal to itself and greater than all other double values (including Double.POSITIVE_INFINITY ). If this and argument both represent Double.NaN, then the equals method returns true, even though Double.NaN==Double.NaN has the value false.
IsNaN returns false if a Double value is either PositiveInfinity or NegativeInfinity. To test for these values, use the IsInfinity, IsPositiveInfinity, and IsNegativeInfinity methods. Converts the string representation of a number to its double-precision floating-point number equivalent.
Floating-point operations return NaN to signal that result of the operation is undefined. For example, dividing 0.0 by 0.0 results in NaN. IsNaN returns false if a Double value is either PositiveInfinity or NegativeInfinity. To test for these values, use the IsInfinity, IsPositiveInfinity, and IsNegativeInfinity methods.
All numeric operations with NaN as an operand produce NaN as a result. As has already been described, NaN is unordered, so a numeric comparison operation involving one or two NaNs returns false and any != comparison involving NaN returns true, including x!=x when x is NaN. Published at DZone with permission of Peter Lawrey, DZone MVB .
Well, according to refrence source, double.IsNegative
just checks the most significant bit:
[Pure]
[System.Security.SecuritySafeCritical] // auto-generated
internal unsafe static bool IsNegative(double d) {
return (*(UInt64*)(&d) & 0x8000000000000000) == 0x8000000000000000;
}
In case of double.NaN
the most signifucant bit is set:
11111111 11111000 00000000 00000000 00000000 00000000 00000000 00000000
|| || |
|<- Exp -><- Mantissa ->
Sign
That's why double.IsNegative
returns true
When we put <
or >
FPU commands are used which know all ones exponent is a special kind of floating point value which should be treated in a special way.
The very same picture is with Single.NaN
.
Note, that we can construct another strange value, negative zero:
10000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000
|| || |
|<- Exp -><- Mantissa ->
Sign
Please, look:
double negativeZero = BitConverter.ToDouble(new byte[] {
0, 0, 0, 0, 0, 0, 0, 128
});
Console.WriteLine(negativeZero == 0 ? "Zero" : "???");
Console.WriteLine(double.IsNegative(negativeZero) ? "Negative" : "???");
The IEEE754 defines floating point numbers. The highest bit is used to define the sign with 0 being positive and 1 being negative.
Through a bit of digging, double.NaN
seems to be represented as 0xFFF8000000000000
in binary (and 0.0 / 0.0
in code somehow).
double.IsNegative(double d)
just checks the highest bit without any actual math being involved. Therefor, NaN is interpreted as a negative value. Meanwhile, double.NaN
if used in a binary comparison will always yield false:
double.NaN < 0.0 //false
double.NaN > 0.0 //false
double.NaN <= 0.0 //false
double.NaN >= 0.0 //false
double.NaN == 0.0 //false
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With