Java计算无效结果



我想确定一个数字的符号,以便在以后的计算中使用。

我有类似下面的代码:

double value = someClass.someGetterMethod();
double sign = value / Math.abs(value);

我也试过了:

double sign = (value < 0) ? -1d : 1d;

不总是,但有时value为正,sign为负。

在非静态方法中,两个变量都在本地堆栈上,所以我认为不存在竞争条件。

不幸的是,我无法发布完整的源代码,也无法在一个较小的示例中复制这一点。我怀疑这与我的环境有关:

所讨论的代码被打包到一个jar中,然后作为zipgroupfileset加载到一个插件jar文件中,该文件由netLogo作为"扩展"(插件)加载。于是NetLogo启动了,它加载了包含这个类的插件jar。

NetLogo要求任何插件都需要为1.5目标编译,所以我在ant构建文件中为库和扩展设置了这个设置。

我通过修改netlogo vmargs来连接netbeans调试器,以允许远程调试

-Xdebug
-Xrunjdwp:transport=dt_socket,address=1000,server=y,suspend=n

我真的难住了。这是调试器如何显示变量的问题吗?也许是NetLogo的1.5编译目标要求有问题?

任何想法?

谢谢

这确实可能是一个显示问题,因为我不明白有问题的代码如何具有您描述的行为。

如果我要解决这个问题,我会让变量final,并在value之后计算sign:

final double value = someClass.someGetterMethod();
final double sign = (value < 0) ? -1d : 1d;

最后,我将在赋值给sign之后打印两个变量。如果在完成所有这些操作后,您可以触发具有不一致符号的valuesign的打印,那么一定有严重、严重的错误。

注:我强烈建议您考虑切换到Math.signum。它可能不会解决您当前的问题,但它会更优雅地处理零和nan。

消除所有歧义的解决方案是将值转换为原始长并检查带符号位的值:

long rawValue = Double.doubleToRawLongBits(value);
boolean isNegative = (rawValue & 0x8000000000000000L) != 0;

为什么sign是double?你觉得这样行吗?

由于浮点数/双精度数的性质,计算符号的第一种方法可能容易产生舍入误差。我会说选择第二种方式:

double value = someClass.someGetterMethod();
int  sign = (value < 0) ? -1 : 1;

最新更新