我有两个双重值。我想检查两个double值是否相同。我有两种比较这个双值的方法。
第一种方式:
double a = 0.1;
double b = 0.2;
if(a == b) {
System.out.println("Double values are same");
}
另一种比较方式:
if(Double.compare(a, b) == 0) {
System.out.println("Double values are same");
}
哪一个是最好的方法和准确?比较双值的两种方式是否相同?
答案 0 :(得分:8)
Double.compare
处理NaN和负零的情况与==
不同。对于Double.compare
,-0.0d
不等于0.0d
。
例如以下代码:
public static void main(String... args) {
double a = -0.0d;
double b = 0.0d;
if (a == b) {
System.out.println("a == b");
}
if (Double.compare(a, b) == 0) {
System.out.println("Double.compare(a, b) == 0");
}
}
只会打印a == b
。
因此这两项操作并不相同。使用其中一个取决于您的要求。
有关==
(和!=
)的确切规则可以在JLS section 15.21.1中找到:
根据IEEE 754标准的规则执行浮点相等测试:
如果任一操作数为NaN,则==的结果为false,但!=的结果为true。实际上,当且仅当x的值为NaN时,测试x!= x才为真。
正零和负零被视为相等。
否则,等于运算符会将两个不同的浮点值视为不相等。特别是,有一个值代表正无穷大,一个值代表负无穷大;每个比较仅与自身相等,每个比较不等于所有其他值。
根据浮点数的这些注意事项,以下规则适用于整数操作数或NaN以外的浮点操作数:
- 如果左侧操作数的值等于右侧操作数的值,则==运算符生成的值为true。否则,结果是错误的。
- 如果左侧操作数的值不等于右侧操作数的值,则由!=运算符生成的值为true。否则,结果是错误的。
答案 1 :(得分:3)
让我们分析这一部分:
if(Double.compare(a, b) == 0)
通过查看Double.compare
的{{3}},可能的实现可能是以下一个(显然它将是一个更优化的实现,但为了讨论的目的) :
return a == b ? 0 : (a < b ? -1 : +1);
然后,你有另一个比较,所以它变成:
if((a == b ? 0 : (a < b ? -1 : +1)) == 0)
在另一种情况下,您依靠使用==
进行简单比较,即:
if(a == b)
那就是说,就准确性而言,我猜结果是一样的,因为double
的基础表示不会改变,与0的比较似乎不会影响准确性。
哪个最好?
嗯,从上面的例子中,我说更简单的一个直接比较价值,你只对平等感兴趣,即使你不太可能面临一个问题,从选择这种比较的最佳方式中受益。
无论如何,使用Double.compare
的方法更适合于那些不仅对等同感兴趣的情况,而且还有大于和/或小于的概念的情况。 EM>
答案 2 :(得分:1)
这两个选项对于检查两个数字的相等性是完全有效的。我个人会说==更好,但那只是我。
当double.compare()更好时,你想知道为什么你的变量不相等。它返回的信息多于真或假 - 如果左侧较小则为负值,如果右侧较小则为正值。