无需终端操作就可以知道流的大小 [英] Is possible to know the size of a stream without using a terminal operation
问题描述
我有3个界面
public interface IGhOrg {
int getId();
String getLogin();
String getName();
String getLocation();
Stream<IGhRepo> getRepos();
}
public interface IGhRepo {
int getId();
int getSize();
int getWatchersCount();
String getLanguage();
Stream<IGhUser> getContributors();
}
public interface IGhUser {
int getId();
String getLogin();
String getName();
String getCompany();
Stream<IGhOrg> getOrgs();
}
,我需要实现Optional<IGhRepo> highestContributors(Stream<IGhOrg> organizations)
此方法返回具有最多贡献者(getContributors())的IGhRepo
this method returns a IGhRepo with most Contributors(getContributors())
我尝试过
Optional<IGhRepo> highestContributors(Stream<IGhOrg> organizations){
return organizations
.flatMap(IGhOrg::getRepos)
.max((repo1,repo2)-> (int)repo1.getContributors().count() - (int)repo2.getContributors().count() );
}
但这给了我
java.lang.IllegalStateException:流已被操作或关闭
java.lang.IllegalStateException: stream has already been operated upon or closed
我了解到count()是Stream中的终端操作,但我无法解决此问题,请帮忙!
I understand that count() is a terminal operation in Stream but I can't solve this problem, please help!
谢谢
推荐答案
您没有指定此名称,但是看起来某些或可能所有返回Stream<...>
值的接口方法都不会返回新鲜的流他们被召唤的时间.
You don't specify this, but it looks like some or possibly all of the interface methods that return Stream<...>
values don't return a fresh stream each time they are called.
从API的角度看,这对我来说似乎很成问题,因为这意味着这些流中的每一个都可以使用,并且该对象功能的相当大一部分最多只能使用一次.
This seems problematic to me from an API point of view, as it means each of these streams, and a fair chunk of the object's functionality can be used at most once.
通过确保每个对象的流在该方法中仅使用一次,您也许可以解决您遇到的特定问题,如下所示:
You may be able to solve the particular problem you are having by ensuring that the stream from each object is used only once in the method, something like this:
Optional<IGhRepo> highestContributors(Stream<IGhOrg> organizations) {
return organizations
.flatMap(IGhOrg::getRepos)
.distinct()
.map(repo -> new AbstractMap.SimpleEntry<>(repo, repo.getContributors().count()))
.max(Map.Entry.comparingByValue())
.map(Map.Entry::getKey);
}
不幸的是,如果您想要打印(例如)贡献者列表,您现在将陷入困境,因为从getContributors()
返回的返回IGhRepo
的流已被消耗.
Unfortunately it looks like you will now be stuck if you want to (for example) print a list of the contributors, as the stream returned from getContributors()
for the returned IGhRepo
has already been consumed.
您可能需要考虑让每次调用流返回方法的实现对象都返回一个新的流.
You might want to consider having your implementation objects return a fresh stream each time a stream returning method is called.
这篇关于无需终端操作就可以知道流的大小的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!