我应该返回一个集合还是一个流? [英] Should I return a Collection or a Stream?

查看:32
本文介绍了我应该返回一个集合还是一个流?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

假设我有一个方法将只读视图返回到成员列表中:

Suppose I have a method that returns a read-only view into a member list:

class Team {
    private List<Player> players = new ArrayList<>();

    // ...

    public List<Player> getPlayers() {
        return Collections.unmodifiableList(players);
    }
}

进一步假设客户端所做的就是立即迭代列表一次.也许将玩家放入 JList 或其他东西.客户端存储对列表的引用以供以后检查!

Further suppose that all the client does is iterate over the list once, immediately. Maybe to put the players into a JList or something. The client does not store a reference to the list for later inspection!

鉴于这种常见情况,我应该返回一个流吗?

Given this common scenario, should I return a stream instead?

public Stream<Player> getPlayers() {
    return players.stream();
}

或者在 Java 中返回一个非惯用的流?流被设计为总是终止"吗?在创建它们的同一个表达式中?

Or is returning a stream non-idiomatic in Java? Were streams designed to always be "terminated" inside the same expression they were created in?

推荐答案

答案一如既往地视情况而定".这取决于返回的集合有多大.这取决于结果是否随时间发生变化,以及返回结果的一致性有多重要.这在很大程度上取决于用户可能如何使用答案.

The answer is, as always, "it depends". It depends on how big the returned collection will be. It depends on whether the result changes over time, and how important consistency of the returned result is. And it depends very much on how the user is likely to use the answer.

首先,请注意,您始终可以从 Stream 中获取 Collection,反之亦然:

First, note that you can always get a Collection from a Stream, and vice versa:

// If API returns Collection, convert with stream()
getFoo().stream()...

// If API returns Stream, use collect()
Collection<T> c = getFooStream().collect(toList());

所以问题是,哪个对您的来电者更有用.

So the question is, which is more useful to your callers.

如果您的结果可能是无限的,那么只有一种选择:Stream.

If your result might be infinite, there's only one choice: Stream.

如果您的结果可能非常大,您可能更喜欢 Stream,因为一次实现它可能没有任何价值,并且这样做可能会产生显着的堆压力.

If your result might be very large, you probably prefer Stream, since there may not be any value in materializing it all at once, and doing so could create significant heap pressure.

如果调用者要做的就是遍历它(搜索、过滤、聚合),你应该更喜欢 Stream,因为 Stream 已经内置了这些并且不需要具体化一个集合(特别是如果用户可能不会处理整个结果.)这是一个非常常见的情况.

If all the caller is going to do is iterate through it (search, filter, aggregate), you should prefer Stream, since Stream has these built-in already and there's no need to materialize a collection (especially if the user might not process the whole result.) This is a very common case.

即使您知道用户将对其进行多次迭代或以其他方式保留它,您仍然可能希望返回一个 Stream,因为简单的事实是,无论 Collection 您选择放入的(例如,ArrayList)可能不是他们想要的形式,然后调用者无论如何都必须复制它.如果您返回一个 Stream,他们可以执行 collect(toCollection(factory)) 并以他们想要的形式获取它.

Even if you know that the user will iterate it multiple times or otherwise keep it around, you still may want to return a Stream instead, for the simple fact that whatever Collection you choose to put it in (e.g., ArrayList) may not be the form they want, and then the caller has to copy it anyway. If you return a Stream, they can do collect(toCollection(factory)) and get it in exactly the form they want.

上面的prefer Stream";案例大多源于 Stream 更灵活的事实;您可以后期绑定到您的使用方式,而不会产生将其具体化到 Collection 的成本和限制.

The above "prefer Stream" cases mostly derive from the fact that Stream is more flexible; you can late-bind to how you use it without incurring the costs and constraints of materializing it to a Collection.

您必须返回 Collection 的一种情况是当有很强的一致性要求时,您必须生成移动目标的一致快照.然后,您需要将元素放入一个不会更改的集合中.

The one case where you must return a Collection is when there are strong consistency requirements, and you have to produce a consistent snapshot of a moving target. Then, you will want put the elements into a collection that will not change.

所以我会说大多数时候,Stream 是正确的答案——它更灵活,它不会强加通常不必要的实现成本,并且可以很容易地变成集合如果需要,您可以选择.但有时,您可能必须返回一个 Collection(例如,由于强一致性要求),或者您可能想要返回 Collection 因为您知道用户将如何使用并且知道这对他们来说是最方便的事情.

So I would say that most of the time, Stream is the right answer — it is more flexible, it doesn't impose usually-unnecessary materialization costs, and can be easily turned into the Collection of your choice if needed. But sometimes, you may have to return a Collection (say, due to strong consistency requirements), or you may want to return Collection because you know how the user will be using it and know this is the most convenient thing for them.

如果您已经有一个合适的 Collection四处闲逛",并且您的用户似乎更愿意将其作为 Collection 与之交互,那么它是一个合理的选择(虽然不是唯一的,而且更脆弱)只返回你所拥有的.

If you already have a suitable Collection "lying around", and it seems likely that your users would rather interact with it as a Collection, then it is a reasonable choice (though not the only one, and more brittle) to just return what you have.

这篇关于我应该返回一个集合还是一个流?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆