【发布时间】:2019-10-03 19:55:09
【问题描述】:
我有两个双精度值(原始类型和非对象!),当我让 Eclipse 为这些双精度值生成 equals/hashCode 时,它将像这样覆盖它:
@Override
public boolean equals(Object obj) {
...
return Double.doubleToLongBits(mydouble) == Double.doubleToLongBits(obj.mydouble) && ..;
}
所以它使用doubleToLongBits 来比较是否相等。但是,当使用 doubleToLongBits 时,0!=-0 的比较返回 false。为什么在equals-方法中需要这个?
我的问题:为什么 Eclipse 不简单地使用
@Override
public boolean equals(Object obj) {
..
return mydouble == obj.mydouble && ..;
}
比较是否相等?这会是错的吗?
问题是特定于原始类型的,以及为什么人们应该使用原始类型而不是简单地使用 doubleToLongBits,例如0.1 == 0.1.
【问题讨论】:
-
如果“mydouble”是一个对象(例如“Double”)而不是一个原始的(“double”)......那确实是错误的。问:您是否期望与 0.0 != -0.0 不同?
-
@paulsm4 不,我的 double 是原始类型。
-
我建议你了解更多关于浮点数的知识。它们本质上是您尝试表示的数字的不精确近似值。如果双精度值是某些计算的结果,这尤其是一个问题。请参阅stackoverflow.com/questions/588004/… 讨论这是如何造成问题的。
-
@NathanHughes 我知道,但是,
==和Double.compare(x,y)的存在是有原因的.. -
还请考虑,对于普通的
==,包含 NaN 作为某些字段值的对象永远不会等于其他任何东西,甚至它本身。如果你把它放到一个集合中,这个集合就会对它撒谎并声称它不包含那个东西。