Java Math.cos()方法在预期时不返回0

在Windows 7 PC上使用Java(不确定是否重要)并在应该返回0的值(如pi / 2)上调用Math.cos()而不是返回小值,但是除非我误解,否则返回的值很小从零开始大于1 ulp。

Math.cos(Math.PI/2) = 6.123233995736766E-17 Math.ulp(Math.cos(Math.PI/2)) = 1.232595164407831E-32 

这实际上是在1 ulp内,我只是感到困惑? 这是否是一个可以接受的解决这种轻微不准确的包装方法?

 public static double cos(double a){ double temp = Math.abs(a % Math.PI); if(temp == Math.PI/2) return 0; return Math.cos(a); } 

不要忘记Math.PI/2是近似值。 它不会完全是 pi / 2,所以cos(Math.PI/2)的结果不会完全为0. Math.cos可能会返回一个非常精确的余弦值,该值是由返回的精确值返回的。计算Math.PI/2

你永远不应该使用==和双打。 您必须始终在误差范围内。 如果你问我,10 -17是很好的精度。 10 -32的 Ulp图只是10 -17数量级的双倍的预先计算,因为2.220446049250313E-16是10 0幅度的数字的精度。

这是一个常见的错误,当你开始时,这个链接有一个非常技术性的讨论原因。 http://docs.sun.com/source/806-3568/ncg_goldberg.html

但是在它最简单的forms中,就像我们不能在十进制系统中完全代表1/3一样,有些值无法在二进制系统中准确表示