我有Stream
指数增长用于创建排列。因此,每次调用addWeeks
都会增加Stream
中的元素数量。
Stream<SeasonBuilder> sbStream = sbSet.stream();
for (int i = 1; i <= someCutOff; i++) {
sbStream = sbStream.map(sb -> sb.addWeeks(possibleWeeks))
.flatMap(Collection::stream);
}
// Collect SeasonBuilders into a Set
return sbStream.collect(Collectors.toSet()); // size > 750 000
addWeeks
都会返回Set<SeasonBuilder>
并将所有内容收集到Set
需要一段时间。 addWeeks
不是静态的,需要在流中的每个SeasonBuilder
上调用,每次循环
public Set<SeasonBuilder> addWeeks(
final Set<Set<ImmutablePair<Integer, Integer>>> possibleWeeks) {
return possibleWeeks.stream()
.filter(containsMatchup()) // Finds the weeks to add
.map(this::addWeek) // Create new SeasonBuilders with the new week
.collect(Collectors.toSet());
内存不足错误.....如果可能,周数大小= 15
map
以外的方法链,然后是 flatmap
吗?addWeeks
以便我不必将所有内容收集到Set
中?
Stream<SeasonBuilder>
吗?我可以flatmap
Stream
吗?感谢大家的帮助!
我已将方法的代码放在gist
中感谢@Holger和@lexicore建议在Stream<SeasonBuilder>
中返回addWeeks
。正如@lexicore预测的那样,性能略有提升
我尝试使用parallelStream()
并且性能没有显着变化
我正在创建Fantasy Football季节的所有可能的排列,这些排列将用于其他地方进行统计分析。在一个为期14周的4人团队中,对于任何一周,可能有三种不同的可能性
要解决这个问题,请插入排列,我们可能会有所有可能的季节。完成!但是等等......如果第1队只参加第2队,那么其他队伍会很伤心。因此对排列有一些限制。
每支球队必须在大致相同的时间内相互比赛(即1队在一个赛季中不能与队3比赛10次)。在这个例子中 - 4支球队,14周 - 每支球队都有5次参加另一支球队的比赛。因此,在创建排列时必须进行某种过滤,以避免无效的季节。
这更有趣的地方是:
我正在尝试尽可能优化性能,因为要创建很多排列。考虑到限制,一个4人队,为期14周的赛季创造了756 756(= 14!/(5!5!4!))可能的赛季。 6队或8队的赛季变得更加疯狂。
答案 0 :(得分:4)
你的整个建筑开始时非常可疑。如果您对性能感兴趣,那么明确生成所有排列不太可能是一种好方法。
我也不相信收集设置和再次流媒体是 性能问题。
但是,回答你的问题:你为什么不直接从Stream<SeasonBuilder>
返回addWeeks
,为什么要收集它先设置?直接返回流,不收集:
public Stream<SeasonBuilder> addWeeks(
final Set<Set<ImmutablePair<Integer, Integer>>> possibleWeeks) {
return possibleWeeks.stream()
.filter(containsMatchup()) // Finds the weeks to add
.map(this::addWeek); // Create new SeasonBuilders with the new week
}
您不需要map
/ flatMap
,只需要一个flatMap
:
sbStream = sbStream.flatMap(sb -> sb.addWeeks(possibleWeeks));
但无论如何这对你的表现都没有帮助。