在c#中检查浮点变量以获得精确值相等的正确方法是什么?

时间:2014-04-13 03:08:13

标签: c# .net floating-point

我需要检查浮点(double)变量a值是否等于浮点(double)变量b值。我知道浮点类型与所有小数值都没有完全匹配,这样的比较并没有太多的"物理意义"但是我仍然需要从二进制的角度检查存储的值是否完全相同。在这种情况下是否正在使用==运算符?

3 个答案:

答案 0 :(得分:8)

如果您要测试两个double是否在数字上相等,则需要测试a == b

如果您要测试两个double s 是否具有相同的二进制表示,则需要首先获取二进制表示。似乎BitConverter.DoubleToInt64Bits是一个可以为您执行此操作的函数。然后在两个位模式之间进行整数比较。

数字相等和逐位相等之间存在一些差异。首先,如果abNaN,那么即使a == ba具有相同的位模式,b也将为false 。其次,IEEE浮点有两个零 - 正零和负零。如果a为正零且b为负零,则a == b将为真,即使ab具有不同的位模式。< / p>

答案 1 :(得分:2)

如果xy都属于double类型,那么x == y当且仅当xy是二进制等效的时候。所以,如果你真正想要的是二元等价,那么==正是你想要使用的。

答案 2 :(得分:1)

对于完全相等,它只是if (a == b)if (a.Equals(b))(注意:如果NaN是{{1}},则这两个表达式的结果可能会有所不同参与。

但是如果你想考虑浮点舍入错误(你应该),那就更复杂了。理论上,您使用double.Epsilon常数来检查数字之间的差异是否在正负epsilon之间结束。在实践中,它通常认为框架错误(see this reference)并且太小了(MSDN文档specifically mentions this - 请参阅页面中间附近的注释),这样你就需要使用你自己的小常数。 1.0e-12或1.0e-15是常见的默认选择,但你真正应该做的是分析数学以确定你的舍入误差实际是什么,并使用&#34; epsilon&#34;基于此,针对您的具体问题保持不变不幸的是,这个过程很容易出错,因此上面提到了常见的默认值。