我正在使用double[]
在C#(。Net 4)中进行一些统计操作,然后我发现CompareTo
方法和double.NaN
有一些奇怪的行为。当我尝试这段代码时:
double.NaN.CompareTo(double.NegativeInfinity) //returns -1
这意味着double.NaN
甚至小于double.NegativeInfinity
!任何人都能解释为什么会这样吗?
答案 0 :(得分:7)
CompareTo并没有告诉你一件事比另一件小。它告诉你一个实例在( - )之后,跟随(+)或在订购实例时可以与(0)另一个实例互换。
为什么这里真的取决于CLR中基元的设计行为。
IComparable的目的是排序类型的实例。因此,对于NaN,一个有效的double值,决定在之前对该类型的任何其他实例进行排序。
请注意,CompareTo在含义或用途上不一定相同,因为数字大于/小于操作。 CompareTo旨在提供双倍可以承担的值集合的排序。例如,
double.NaN.CompareTo(double.NaN)
将返回0.但是
double.NaN == double.NaN
是假的。同样地,
double.NaN.CompareTo(double.NegativeInfinity)
返回-1,但
double.NaN < double.NegativeInfinity
返回false。因此,CompareTo方法并不是说数学上是double.NaN小于double.NegativeInfinity。事实上,小于运营商说这不是真的。但是它说,在订购价值时,double.NaN首先出现。
以下是Double类型的LessThan Operator文档的链接。同时阅读IComparable.CompareTo的含义应该有助于澄清两种方法试图表达的差异。
答案 1 :(得分:6)
double.NaN
小于负无穷大。
从他们解释的元数据信息中可以看出;
public const double NegativeInfinity = -1.0 / 0.0
public const double NaN = 0.0 / 0.0;
来自Double.CompareTo()
方法;
将此实例与指定的双精度浮点值进行比较 number并返回一个整数,指示是否为this的值 instance小于,等于或大于the的值 指定的双精度浮点数。
如果此实例不是数字(NaN)且值是数字
Double.CompareTo()
方法返回负整数
我们来看看这个示例(这里是 DEMO
);
void Main()
{
double a = double.NaN;
double b = double.NegativeInfinity;
Console.WriteLine(a.CompareTo(b));
}
即使我们查看IL代码,double.NaN
代表00 00 00 00 00 00 F8 FF
而double.NegativeInfinity
代表00 00 00 00 00 00 F0 FF
;
IL_0000: ldc.r8 00 00 00 00 00 00 F8 FF
IL_0009: stloc.0
IL_000A: ldc.r8 00 00 00 00 00 00 F0 FF
IL_0013: stloc.1
IL_0014: ldloca.s 00
IL_0016: ldloc.1
IL_0017: call System.Double.CompareTo
IL_001C: call System.Console.WriteLine
答案 2 :(得分:0)
在一天结束时,将double.nan数字与任何事物进行比较是毫无意义的。但是如果你有一个双重列表并希望对它做一些事情,那么你需要在列表末尾全部完成它们,这样你就可以先做所有有意义的工作,这样你就可以在看到第一个时停下来一。它就像一个列表,其中一些项目为空,它们被推到最后。
发生double.nan的一些情况:
Dim d1 as double = 0/0
Dim d2 as double = Double.PositiveInfinity / Double.PositiveInfinity
Dim d3 as double = Double.PositiveInfinity / Double.NegativeInfinity
Dim d4 as double = Double.PositiveInfinity / Double.PositiveInfinity
Dim d5 as double = Double.PositiveInfinity / Double.NegativeInfinity