3
Double out = otherTypes.someMethod(c, c2);
assertEquals((Double)-1.0D, out);

我收到错误“无法解决双精度数”(assertEquals 中的双精度数),除了提取变量之外,还有什么方法可以破解它?

是 Java 中的这个错误还是只是非常有用的功能无法修复?

4

5 回答 5

6

一个重要的注意事项:由于浮点数的工作方式,您永远不应该直接比较两个双精度数(或通常所说的浮点数)是否相等,如果它们的差异在指定的 delta: 内,请始终进行比较abs(double1 - double2) < delta

JUnit 有一种assertEquals(double expected, double actual, double delta)方法可以做到这一点。也就是说,您可能应该使用类似的东西

assertEquals(-1.0d, (double) out, 0.000001d)

在你的代码中。

您可以在例如 Brian Goetz 的一篇文章中找到更多关于浮点数的技巧和陷阱的信息:“你的观点在哪里?”

于 2008-10-22T07:33:17.050 回答
2

我的变化类似于 jjnguy 的

assertEquals(Double.valueOf(-1.0D), out)

这个最大的区别是 Double.valueOf 可以返回一个缓存副本,而不必创建一个新对象。

于 2008-10-22T06:38:08.097 回答
1

要将 -1.0D 转换为 Double,我们通常使用 Double.valueOf(-1.0D) 的最佳方式。Double 类缓存对 valueOf 的调用结果,因此您不会总是在堆上创建新对象。但更好的是转换成双倍,这样更便宜。用于out.doubleValue()获取双精度值。唯一需要注意的是 out 可能为空,这是一个单独的案例,可能值得单独检测。

在以这种方式测试直接相等时,您还应该警惕浮点不准确性。理论上相等的两个数字可能不具有完全相等的表示,因为大多数浮点运算都会引入一些舍入误差。在这种情况下可行的一个简单解决方案是测试差异是否小于某个增量:

assertTrue(Math.abs(-1.0D-out.doubleValue()) < delta);

您还可以使用 JUnit 的便捷方法来执行此操作:

assertEquals(-1.0d, out.doubleValue(), delta);

对 delta 使用非常小的值,例如 10E-10,或者适合您的应用程序的值。在最一般的情况下,如果您不知道要比较的值的范围,则需要将 delta 乘以每个数字的相对大小,如下所示:

double tDelta = delta*(Math.abs(-1.0D)+Math.abs(out.doubleValue()));
assertEquals(-1.0d, out.doubleValue(), tDelta);

如果您要比较非常大的数字,您希望允许的增量更大,如果您要比较非常小的数字,您希望允许的增量更小。但是对于您的情况,您事先知道您的参数之一,因此您可以对增量进行硬编码。

于 2008-10-22T20:16:27.913 回答
0

当您想检查两个双打是否完全相同时,我的建议是:

assertEquals(Double.doubleToLongBits(-1.0), Double.doubleToLongBits(out));
于 2008-10-22T08:56:22.047 回答
0

This goes through the compiler:

assertEquals(Double.class.cast(-1.0D), out);
于 2008-10-22T11:26:27.000 回答