在 Java 中求和时出现 NaN 错误



我在大学里做项目,我面临着一个严重的问题。事实上,我的代码是将 2 个变量相加,以便之后做一些员工。正如我将在下面显示的,列表不是空的,代码从列表中提取值,但 while 但它不会增加计数器。如果有人能给我一些帮助,我将不胜感激。

//CHeck if we have already imported data, if yes we use it, unless we import
if ((this.stockHistory != null) && (!(this.stockHistory.isEmpty())))
{
evolution = this.stockHistory;
}
else 
{
evolution = getHostoricalData(cloned);
}
// Here I am sure the list ( evolution ) is not empty, in my case it has 63 elements
double spot ;
double sommeTendance = 0 ;
double sommeVarianceQuotidienne = 0 ;
for (int i=0;i<evolution.size()-1; i++)
{
double i1 =evolution.get(i+1) ;
System.out.println(" i1 = " + i1);
double i0 = evolution.get(i) ;
System.out.println("i0 is " + i0);
sommeTendance+= Math.log(i1/i0);
System.out.println("tendance == " +sommeTendance);
sommeVarianceQuotidienne += Math.pow(Math.log(i1/i0),2);
System.out.println("variance daily  == " + sommeVarianceQuotidienne);
}
System.out.println("size == " + evolution.size());
System.out.println("total tendance == " + sommeTendance);
System.out.println("total daily variance == " + sommeVarianceQuotidienne);

这是输出的最后一行

16:59:52,524 INFO  [stdout] (default task-62)  i1 = 51.619999
16:59:52,524 INFO  [stdout] (default task-62) i0 is 52.73
16:59:52,524 INFO  [stdout] (default task-62) tendance == NaN
16:59:52,524 INFO  [stdout] (default task-62) variance daily  == NaN
16:59:52,524 INFO  [stdout] (default task-62)  i1 = 53.330002
16:59:52,524 INFO  [stdout] (default task-62) i0 is 51.619999
16:59:52,525 INFO  [stdout] (default task-62) tendance == NaN
16:59:52,525 INFO  [stdout] (default task-62) variance daily  == NaN
16:59:52,525 INFO  [stdout] (default task-62) size == 63
16:59:52,525 INFO  [stdout] (default task-62) total tendance == NaN
16:59:52,525 INFO  [stdout] (default task-62) total daily variance == NaN

首先,您需要了解 NaN 代表什么。Nan 代表 不是一个数字。

你如何获得 NaN?

如果浮点运算有一些输入,则生成"Nan" 导致操作产生一些未定义结果的参数。

什么可能导致 NaN?

例如,0.0

除以 0.0 在算术上是未定义的。发现 负数的平方根也是未定义的。

所有以 NaN 为操作数的数字运算都会产生 NaN。 这背后的原因是NaN是无序的,所以数值比较 涉及一个或两个 NaN 的操作返回 false。

既然我们完全了解 NaN,现在让我们围绕解决方案进行研究。


在您的情况下,NaN 由Math.log(i1/i0);对数函数未在 (-oo,0( 上定义。因此,作为参数Math.log(i1/i0);输入的每个负数都将返回 NaN 作为 java 中的结果。

你能做什么?

-> 在 i1/i0 上构建一个小测试,然后再将其作为参数传递Math.log()


建议:

for (int i=0;i<evolution.size()-1; i++)
{
double i1 =evolution.get(i+1) ;
double i0 = evolution.get(i) ;
if (i1/i0>0)
{
//you are good 
sommeTendance+= Math.log(i1/i0);
sommeVarianceQuotidienne += Math.pow(Math.log(i1/i0),2);
}
else
{
//you are not good, the number will yield an undefined result 
//do something else... like displaying an error....?
System.out.println("Math.log will yield into an undefined result. Please check your input");
}
}

有用的链接:

  • https://www.avocado.com.au/resources/tech-tips/java-double-nan-weirdness/
  • https://www.geeksforgeeks.org/nan-not-number-java/

希望这有帮助。

最新更新