这个问题与euler project sum-of-primes, and Stream.view有关,但有一点扭曲。我想计算低于200万的所有素数的总和。我创建了一个素数生成器,定义为:
lazy val primes: Stream[Int] = 2 #:: Stream.from(3).filter(i =>
primes.takeWhile(j => j * j <= i).forall(i % _ > 0))
我写了两个测试,一个使用Stream [Int] #foldLeft,一个使用Stream [Int] #sum:
@Test
def testEuler010a {
primes.view.takeWhile(_ < 2000000).foldLeft(0L)(_ + _) mustEqual 142913828922L
}
@Test
def testEuler010b {
primes.view.takeWhile(_ < 2000000).sum mustEqual 142913828922L
}
testEuler010a
为我提供了正确的答案,而testEuler010b
没有回答1179908154
。我希望Stream[Int]#foldLeft(0L)(_ + _)
与Stream[Int].sum
相同,但事实并非如此。即使我使用toList()
实现了Stream,我也会遇到相同的差异。这些方法应该给出相同的结果是不正确的假设吗?
我正在使用Scala 2.9.1.final。
答案 0 :(得分:11)
问题似乎是溢出。这些给我的结果相同:
(primes map (_.longValue) takeWhile (_ < 2000000)).sum
(primes map (_.longValue) takeWhile (_ < 2000000)).foldLeft(0L)(_ + _)
我认为sum
和foldLeft
之间的区别在于sum
的结果类型与要求的元素类型相同({{3}所要求的}}),但foldLeft
可以有不同的结果类型,您可以通过编写0L
来实现。