欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

Java中如何比较浮点数是否相等

程序员文章站 2022-03-30 17:11:32
...

0.前言

所谓“相等”,有两种理解,一种是浮点数的值相等,另一种是指对象相同。

1.值相等

浮点数能表示的精度是有限的,在计算过程中不可避免的会出现截尾而损失精度,而且传感器等外部设备输入的数据本身也有误差,所以如果要判断一个浮点数double_x是否等于0,用double_x == 0这样的判断是不合适的,如果double_x是一系列计算的结果或者是外部传感器的输入值,那么它几乎不可能是0,它大概率是一个接近0的小数,比如0.000002,那么,这时候要比较double_x是否等于0,首先要明确自己的精度要求,比如因为传感器有误差,小于0.001的数都可以认为等于0,那么就定义epsilon=0.001:

final double epsilon = 0.001;
if(Math.abs(double_x - 0) < epsilon)
{
    return true;
}

2.对象相同

判断两个double变量值严格相等,一般会直接用double_x == double_y来做比较,这样做一般没有问题,但是如果本意是比较两个浮点数对象是否相同(double_x == double_y是比较两个对象值是否严格相同),对象相同和值严格相等是不一样的,原因是java遵循IEEE 754浮点数标准,在这个标准中规定NaN与任何值比较皆不等,如果double_xdouble_y的值都是NaN,这个时候他们是相同的对象,但double_x == double_y会返回false。解决方法是,判断浮点数对象是否相同,要用Double.doubleToLongBits将double值转换过后再比较

if(Double.doubleToLongBits(double_x) == Double.doubleToLongBits(double_y))

Double.doubleToLongBits说明:

Returns a representation of the specified floating-point value according to the IEEE 754 floating-point “double format” bit layout.
Bit 63 (the bit that is selected by the mask 0x8000000000000000L) represents the sign of the floating-point number. Bits 62-52 (the bits that are selected by the mask 0x7ff0000000000000L) represent the exponent. Bits 51-0 (the bits that are selected by the mask 0x000fffffffffffffL) represent the significand (sometimes called the mantissa) of the floating-point number.

If the argument is positive infinity, the result is 0x7ff0000000000000L.

If the argument is negative infinity, the result is 0xfff0000000000000L.

If the argument is NaN, the result is 0x7ff8000000000000L.

In all cases, the result is a long integer that, when given to the longBitsToDouble(long) method, will produce a floating-point value the same as the argument to doubleToLongBits (except all NaN values are collapsed to a single “canonical” NaN value).