为什么都c1和c2不被视为两个字符串,而是一个String和一个Integer?
Arrays.asList("duck","chicken","flamingo","pelican")
.stream()
.reduce(0,
(c1, c2) -> c1.length() + c2.length(),
(s1, s2) -> s1 + s2);
Run Code Online (Sandbox Code Playgroud)
该方法有三种reduce变体,其签名和返回类型有所不同。如果您查看reduce具有此签名的重载:
reduce(U identity, BiFunction<U,? super T,U> accumulator, BinaryOperator<U> combiner)
Run Code Online (Sandbox Code Playgroud)
从方法签名中可以看出,此重载reduce有 3 个参数:identity、accumulator 和combiner。身份值是您传递给reduceie ( 0) 的初始值,然后我们有累加器,它基本上将附加元素合并到结果中,最后,组合器的工作是将提供的两个值组合起来。
所以你问:
为什么 c1 和 c2 不被视为两个字符串,而是一个字符串和一个整数?
第一个参数在您的情况下是BiFunction这样,因此,用于标识值的类型必须与第一个参数的类型以及累加器函数()的返回类型相同。UIntegerBiFunction
除此之外,您需要更改此设置:
(c1, c2) -> c1.length() + c2.length()
Run Code Online (Sandbox Code Playgroud)
对此:
(c1, c2) -> c1 + c2.length()
Run Code Online (Sandbox Code Playgroud)
需要注意的是,combiner函数 (s1, s2) -> s1 + s2根本不会被调用。原因是这个特定的重载被设计为与 一起使用parallelStream,因此为了使组合器工作,流必须是并行的。否则,只会调用累加器函数。
另一方面,您的完整代码可以简化为:
int result = Stream.of("duck","chicken","flamingo","pelican")
.reduce(0,
(c1, c2) -> c1 + c2.length(),
(s1, s2) -> s1 + s2);
Run Code Online (Sandbox Code Playgroud)
如果您想避免装箱/拆箱的开销,甚至更好reduce:
int result = Stream.of("duck", "chicken", "flamingo", "pelican")
.mapToInt(String::length)
.sum();
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
189 次 |
| 最近记录: |