b/w foldLeft 和 Java collect 有什么区别
What's the difference b/w foldLeft and Java collect
此问题针对 Vavr(Java 的 FP 库),但可能适用于 Scala 或其他可以与 Java 相比的 FP 语言。
Vavr有什么区别foldLeft
:
-
<U> U foldLeft(U zero,
BiFunction<? super U, ? super T, ? extends U> combiner)
和Java的collect
:
-
<R> R collect(Supplier<R> supplier,
BiConsumer<R, ? super T> accumulator,
BiConsumer<R, R> combiner)
似乎两者都可以实现相同的目的:通过遍历集合并将结果累加到新类型U
(或R
)来转换集合(比如Stream<T>
),而遍历.
乍一看,签名在#arguments 中有所不同,Java collect
似乎是 运行 并行块。
概念上有哪些实际差异? Vavr foldLeft
似乎更容易使用。
非常愚蠢的例子只是为了说明:
Vavr foldLeft
:
// result = "HelloFunctionalWorld"
String result = Seq("Hello", "Functional", "World")
.foldLeft(new StringBuilder(), (acc, word) -> acc.append(word))
.toString();
Java collect
:
// result = "HelloFunctionalWorld"
final String result = Arrays.asList("Hello", "Functional", "World").stream()
.collect(
StringBuilder::new,
(acc, word) -> acc.append(word),
StringBuilder::append
)
.toString();
Which are the actual differences conceptually?
正如 collect(Supplier<R> supplier, BiConsumer<R,? super T> accumulator, BiConsumer<R,R> combiner)
的 javadoc 所说:
Performs a mutable reduction operation on the elements of this stream. A mutable reduction is one in which the reduced value is a mutable result container, such as an ArrayList
, and elements are incorporated by updating the state of the result rather than by replacing the result. This produces a result equivalent to:
R result = supplier.get();
for (T element : this stream)
accumulator.accept(result, element);
return result;
这里的关键词是可变,因为 Vavr 不做任何可变的事情,是一个功能库。
题目中使用StringBuilder
的例子其实是违反函数式原则的。如果您不打算遵循功能范例,为什么要使用 Vavr?
Java 流相当于 foldLeft()
is reduce()
,你说得对,第三个参数是支持并行处理:
// Vavr
<U> U foldLeft(U zero,
BiFunction<? super U,? super T,? extends U> combine)
// Java Stream
<U> U reduce(U identity,
BiFunction<U,? super T,U> accumulator,
BinaryOperator<U> combiner)
如果结果类型与流元素类型相同,您将使用以下替代方案,不需要第三个参数来支持并行处理:
// Vavr
T fold(T zero,
BiFunction<? super T,? super T,? extends T> combine)
// Java Stream
T reduce(T identity,
BinaryOperator<T> accumulator)
更新方法比较:
Vavr
T fold(T zero, BiFunction<? super T,? super T,? extends T> combine)
以任意顺序应用 combine
,因此它必须是一个 关联 函数。
<U> U foldLeft(U zero, BiFunction<? super U,? super T,? extends U> combine)
应用来自 left-to-right.
的值
相当于顺序模式中的reduce(identity, accumulator, combiner)
,其中combiner
未使用。 并行模式 支持有效的 combiner
函数。
<U> U foldRight(U zero, java.util.function.BiFunction<? super T,? super U,? extends U> combine)
应用来自 right-to-left.
的值
否 Java 等效流。
Java 流
Optional<T> reduce(BinaryOperator<T> accumulator)
以任意顺序应用accumulator
,因此它必须是关联函数。例如。流 1,2,3,4
和 +
可以处理为 ((1+2)+3)+4
(顺序模式),或 (1+2)+(3+4)
,1+((2+3)+4)
或任何顺序组合(并联方式).
没有等效的 Vavr。
T reduce(T identity, BinaryOperator<T> accumulator)
以任意顺序应用accumulator
,因此它必须是关联函数。例如。使用 0
和 +
流式传输 1,2,3,4
可以作为 (((0+1)+2)+3)+4
(顺序模式) 或 ((0+1)+2) + ((0+3)+4)
或任何顺序组合(并联方式).
<U> U reduce(U identity, BiFunction<U,? super T,U> accumulator, BinaryOperator<U> combiner)
按顺序应用值,combiner
支持并行处理。
顺序模式等同于foldLeft(zero, combine)`.
<R> R collect(Supplier<R> supplier, BiConsumer<R,? super T> accumulator, BiConsumer<R,R> combiner)
在sequential模式下,supplier
用于创建一个mutable结果容器,然后按顺序应用值.在 并行模式 中,创建多个可变结果容器并填充值,然后使用 combiner
函数合并。
没有等效的 Vavr。
此问题针对 Vavr(Java 的 FP 库),但可能适用于 Scala 或其他可以与 Java 相比的 FP 语言。
Vavr有什么区别foldLeft
:
-
<U> U foldLeft(U zero, BiFunction<? super U, ? super T, ? extends U> combiner)
和Java的collect
:
-
<R> R collect(Supplier<R> supplier, BiConsumer<R, ? super T> accumulator, BiConsumer<R, R> combiner)
似乎两者都可以实现相同的目的:通过遍历集合并将结果累加到新类型U
(或R
)来转换集合(比如Stream<T>
),而遍历.
乍一看,签名在#arguments 中有所不同,Java collect
似乎是 运行 并行块。
概念上有哪些实际差异? Vavr foldLeft
似乎更容易使用。
非常愚蠢的例子只是为了说明:
Vavr foldLeft
:
// result = "HelloFunctionalWorld"
String result = Seq("Hello", "Functional", "World")
.foldLeft(new StringBuilder(), (acc, word) -> acc.append(word))
.toString();
Java collect
:
// result = "HelloFunctionalWorld"
final String result = Arrays.asList("Hello", "Functional", "World").stream()
.collect(
StringBuilder::new,
(acc, word) -> acc.append(word),
StringBuilder::append
)
.toString();
Which are the actual differences conceptually?
正如 collect(Supplier<R> supplier, BiConsumer<R,? super T> accumulator, BiConsumer<R,R> combiner)
的 javadoc 所说:
Performs a mutable reduction operation on the elements of this stream. A mutable reduction is one in which the reduced value is a mutable result container, such as an
ArrayList
, and elements are incorporated by updating the state of the result rather than by replacing the result. This produces a result equivalent to:R result = supplier.get(); for (T element : this stream) accumulator.accept(result, element); return result;
这里的关键词是可变,因为 Vavr 不做任何可变的事情,是一个功能库。
题目中使用StringBuilder
的例子其实是违反函数式原则的。如果您不打算遵循功能范例,为什么要使用 Vavr?
Java 流相当于 foldLeft()
is reduce()
,你说得对,第三个参数是支持并行处理:
// Vavr
<U> U foldLeft(U zero,
BiFunction<? super U,? super T,? extends U> combine)
// Java Stream
<U> U reduce(U identity,
BiFunction<U,? super T,U> accumulator,
BinaryOperator<U> combiner)
如果结果类型与流元素类型相同,您将使用以下替代方案,不需要第三个参数来支持并行处理:
// Vavr
T fold(T zero,
BiFunction<? super T,? super T,? extends T> combine)
// Java Stream
T reduce(T identity,
BinaryOperator<T> accumulator)
更新方法比较:
Vavr
T fold(T zero, BiFunction<? super T,? super T,? extends T> combine)
以任意顺序应用
combine
,因此它必须是一个 关联 函数。<U> U foldLeft(U zero, BiFunction<? super U,? super T,? extends U> combine)
应用来自 left-to-right.
的值相当于顺序模式中的
reduce(identity, accumulator, combiner)
,其中combiner
未使用。 并行模式 支持有效的combiner
函数。<U> U foldRight(U zero, java.util.function.BiFunction<? super T,? super U,? extends U> combine)
应用来自 right-to-left.
的值否 Java 等效流。
Java 流
Optional<T> reduce(BinaryOperator<T> accumulator)
以任意顺序应用
accumulator
,因此它必须是关联函数。例如。流1,2,3,4
和+
可以处理为((1+2)+3)+4
(顺序模式),或(1+2)+(3+4)
,1+((2+3)+4)
或任何顺序组合(并联方式).没有等效的 Vavr。
T reduce(T identity, BinaryOperator<T> accumulator)
以任意顺序应用
accumulator
,因此它必须是关联函数。例如。使用0
和+
流式传输1,2,3,4
可以作为(((0+1)+2)+3)+4
(顺序模式) 或((0+1)+2) + ((0+3)+4)
或任何顺序组合(并联方式).<U> U reduce(U identity, BiFunction<U,? super T,U> accumulator, BinaryOperator<U> combiner)
按顺序应用值,
combiner
支持并行处理。顺序模式等同于foldLeft(zero, combine)`.
<R> R collect(Supplier<R> supplier, BiConsumer<R,? super T> accumulator, BiConsumer<R,R> combiner)
在sequential模式下,
supplier
用于创建一个mutable结果容器,然后按顺序应用值.在 并行模式 中,创建多个可变结果容器并填充值,然后使用combiner
函数合并。没有等效的 Vavr。