我有三个无限的Java IntStream
对象。我想找到这三个元素中存在的最小元素。
IntStream a = IntStream.iterate(286, i->i+1).map(i -> (Integer)i*(i+1)/2);
IntStream b = IntStream.iterate(166, i->i+1).map(i -> (Integer)i*(3*i-1)/2);
IntStream c = IntStream.iterate(144, i->i+1).map(i -> i*(2*i-1));
我总是可以使用暴力解决方案(没有流),这涉及在嵌套循环中进行迭代,但我想知道我们是否可以使用流更有效地执行它?
答案 0 :(得分:2)
你需要并行迭代所有3个,推进具有最低值的那个,检查所有3个是否相等。
您的代码无法在40755
之后找到下一个值的答案,因为下一个值为1_533_776_805
,其中间值(除以2之前)高于Integer.MAX_VALUE
({ {1}})。
因此,在将这些流更改为2_147_483_647
并防止溢出后,这是一种使用流的方法。
long
答案 1 :(得分:0)
这些功能总是在增加。所以代码应该在找到魔法相等的三元组时停止。
要编码的是:
a)当流的当前值低于任何其他值时,它可以为自己迭代。
b)当它遇到相同的候选值时,它等待第3个流做出决定。
c)当它的值高于其他所有值时,它会改变候选人并等待其他人。
参考杂耍。
也可能没有解决方案(至少在短时间内)。
请注意,流c只能产生偶数(当用偶数播种时)。可能会有一些优化可以更快地跳过a和b。
答案 2 :(得分:0)
我认为流API没有任何智能可行。主要原因是,在满足某些条件之前,您无法真正查看一个流 - 而是在查看当前的3个元素并从其中一个流中选择下一个元素,然后再次比较这些元素。
最有效(也可能是最干净)的解决方案是使用迭代器并在正确的流上继续调用next()
方法,直到找到答案。
首先,您可以只关注两个流并找到它们的第一个共同值:
while (elementA != elementB) {
if (elementA < elementB) {
elementA = iteratorA.next();
} else {
elementB = iteratorB.next();
}
}
然后你需要让第三个流赶上这两个:
while (elementC < elementA) {
elementC = iteratorC.next();
}
此时有两种选择:
elementC == elementA
,在这种情况下,您有答案elementC > elementA
在这种情况下,您可以转到所有三个流的下一个值并重新开始要记住的一件事是整数的最大值。因为你有i^2
,这意味着它会溢出i
大约46k,所以你需要将整数流改为longs流(答案是大约15亿 - 而且是在除以2之后在这些功能中)。
由于你正在练习练习,我认为给你完整的工作代码是不对的,但如果你仍然在努力,请告诉我;)