Java中的stream.max(Comparator)和stream.collect(Collectors.maxBy(Comparator))之间的区别

时间:2018-09-29 18:24:55

标签: api java-8 java-stream collectors

在Java Streams中-stream.max(Comparator)stream.collect(Collectors.maxBy(Comparator))在性能方面有何区别?两者都将根据通过的比较器获取最大值。如果是这种情况,为什么我们需要使用collect方法进行收集的附加步骤?我们什么时候应该选择前者还是后者?什么情况适合同时使用?

3 个答案:

答案 0 :(得分:5)

他们做同样的事情,并共享相同的代码。

  

为什么我们需要使用collect方法进行收集的额外步骤?

你不知道。如果您要这样做,请使用max()。但是在某些情况下,收集器可以派上用场。例如:

Optional<Foo> result = stream.collect(createCollector());

其中createCollector()将基于某种条件(可能是maxBy,minBy或其他条件)返回收集器。

通常,您不应该太在乎两种执行相同操作的方法之间可能存在的微小性能差异,并且有很大的机会以相同的方式实现。相反,您应该使代码尽可能清晰易读。

答案 1 :(得分:4)

有效Java 第三版,第214页中有相关的报价:

  

counting方法返回的收集器仅供 用作下游收集器。通过Stream方法可以直接在count上使用相同的功能,因此从来没有理由说collect(counting()) 。此属性还有15个Collectors

鉴于maxByStream.max复制,大概是这16种方法之一。

在同一页上不久,它继续证明双重存在的合理性:

  

从设计的角度来看,这些收集器表示尝试部分复制收集器中流的功能,以便下游收集器可以充当“微型流”。

我个人觉得这个法令和解释有点令人不满意:它说这16个收集器不是这样的意图,但不是为什么他们 t

我认为直接在流上的方法能够以专门的方式实现,这可能比一般的收集器更有效。

答案 2 :(得分:0)

根据Java文档

以下是maxBy,minBy来自Collectors类的定义,

static <T> Collector<T,?,Optional<T>> maxBy(Comparator<? super T> comparator)

返回一个收集器,该收集器根据给定的Comparator(描述为Optional<T>)产生最大元素。

static <T> Collector<T,?,Optional<T>> minBy(Comparator<? super T> comparator)

返回一个收集器,该收集器根据给定的Comparator(称为Optional<T>)产生最小的元素。

其中max()中的min()Stream返回Optional<T>

每个流管道操作可以分为终端操作和非终端操作。 因此,根据java doc的定义,很明显,提供max()min()的Stream是终端操作并返回Optional<T>

但是maxBy()minBy()是收集器生成操作,因此可以用于链接计算。