我想,由于浮点限制,sm和sm2是不相等的:
double sm = -1.22 + (0.6027852837247973 + 0.8920332205475238);
double sm2 = -1.22 + 0.6027852837247973 + 0.8920332205475238;
System.out.println("sm = "+sm);
System.out.println("sm2 = "+sm2);
System.out.println("sm-sm2 = "+(sm-sm2));结果是:
sm = 0.27481850427232124
sm2 = 0.27481850427232113
sm-sm2 = 1.1102230246251565E-16我想不是因为操作顺序而是零的吧?
无论如何,在本例中,我想问的是-如何获得与此代码相当的代码:
double r2 = 0;
for(double o : ar){
r2+=o*2;
}
r2 -= k;在功能风格(例如,像这样,但由于它是第一次操作,我有问题的输出):
Arrays.stream(ar)
.map(o -> o*2)
.reduce(-k, Double::sum);发布于 2019-11-18 18:39:52
正如您在问题中提到的,操作顺序关系到。当您使用流时,无法保证执行的顺序。此外,在使用流的方法中还有另一个问题,那就是identity参数的值--在您的情况下是k (我假设您希望从结果中减去一些非零值)。reduce(double identity, DoubleBinaryOperator accumulator)中标识和累加器函数的值必须使下列语句始终为真:
accumulator.apply(identity, x) = x // for any value of x具有累加器Double::sum (与(d1, d2) -> Double.sum(d1, d2)相同),有效标识的唯一值是0。
JavaDoc参考资料:
double java.util.stream.DoubleStream.reduce(双重身份,DoubleBinaryOperator op)
使用提供的标识值和关联累加函数对该流的元素执行约简,并返回还原值。这相当于:
双重结果=标识;对于(双元素:此流)结果=accumulator.applyAsDouble(结果,元素)返回结果;
但不被限制按顺序执行。标识值必须是累加器函数的标识。这意味着对于所有的x,accumulator.apply(恒等式,x)等于x。累加器函数必须是一个结合函数。
这是终端操作.
您可以尝试这样的方法(正如@VLAZ建议的那样):
double calculate(double[] values, double k) {
return DoubleStream.of(values).map(d -> d * 2).reduce(0, Double::sum) - k;
}
更新
正如@LouisWasserman所建议的,calculate方法可以通过将reduce(0, Double::sum)替换为sum()来简化
double calculate(double[] values, double k) {
return DoubleStream.of(values).map(d -> d * 2).sum() - k;
}https://stackoverflow.com/questions/58919868
复制相似问题