什么相当于 Java 8 中 Scala 伟大的 foldLeft
?
我很想它是 reduce
,但 reduce 必须返回与它所归约的类型相同的东西。
例子:
import java.util.List;
public class Foo {
// this method works pretty well
public int sum(List<Integer> numbers) {
return numbers.stream()
.reduce(0, (acc, n) -> (acc + n));
}
// this method makes the file not compile
public String concatenate(List<Character> chars) {
return chars.stream()
.reduce(new StringBuilder(""), (acc, c) -> acc.append(c)).toString();
}
}
上面代码的问题是acc
umulator:new StringBuilder("")
因此,谁能指出我的 foldLeft
/fix my code 的正确等效项?
最佳答案
Java 8 的 Stream API 中没有 foldLeft
的等价物。正如其他人所指出的, reduce(identity, accumulator, combiner)
很接近,但它与 foldLeft
不等价,因为它需要生成的类型 B
与自身结合并具有关联性(换句话说,是类幺半群),并非每种类型都具有的属性。
还有一个增强请求:add Stream.foldLeft() terminal operation
要了解为什么 reduce 不起作用,请考虑以下代码,您打算在其中执行从给定数字开始的一系列算术运算:
val arithOps = List(('+', 1), ('*', 4), ('-', 2), ('/', 5))
val fun: (Int, (Char, Int)) => Int = {
case (x, ('+', y)) => x + y
case (x, ('-', y)) => x - y
case (x, ('*', y)) => x * y
case (x, ('/', y)) => x / y
}
val number = 2
arithOps.foldLeft(number)(fun) // ((2 + 1) * 4 - 2) / 5
如果您尝试编写 reduce(2, fun, combine)
,您可以传递什么组合器函数来组合两个数字?将这两个数字加在一起显然不能解决问题。此外,值 2
显然不是 identity 元素。
请注意,任何需要顺序执行的操作都不能用 reduce
表示。 foldLeft
实际上比 reduce
更通用:你可以用 foldLeft
实现 reduce
但你不能实现 foldLeft
与 reduce
。
关于java - 等效于 Java 8 中的 Scala 的 foldLeft,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/41240414/