Java stream.mapToDouble.sum的精度问题
Java 里的 double 类型的精度问题,是一个老生常谈的问题了,现在我们在 Java 8 中通常用 BigDecimal 来解决这个问题,但最近在做一些功能时还是碰到了 double 的精度带来的一些困扰。
先上一段伪代码
1 |
|
此时将 Bean.amount 转成 double 再 sum 操作后,sumAmount 出现了精度问题。
但由于 stream() 并没有提供直接操作 BigDecimal 的方法,那么有没有办法简单地将这个精度问题解决掉呢?还是有的。
使用 reduce() 方法,这个方法是 Stream 的一个聚合方法,可以把 Stream 中的所有元素按照聚合函数聚合成一个结果。
按照这个思路进行修改后的伪代码
1 |
|
首先使用 map() 将需要操作的元素拿出来,然后通过 reduce() 来使用 BigDecimal 的 add() 方法来实现累加。
reduce() 有三个 override 实现方法:
T reduce(T identity, BinaryOperator<T> accumulator);Optional<T> reduce(BinaryOperator<T> accumulator);<U> U reduce(U identity, BiFunction<U, ? super T, U> accumulator, BinaryOperator<U> combiner);
这里我们使用的是第一个,identity 是用于执行 accumulator 的初始值,如果 list 是空值,那么就会直接返回 indentity 的值。