2010-06-02 4 views
7

Я определяю поток в терминах самого себя (рекурсивное определение). При попытке доступа к второму элементу потока, бросается StackOverflowError. Код из консоли scala:Рекурсивный поток бросает StackOverflowError

scala> val s1 = Stream.iterate(1)(identity _) 
s1: scala.collection.immutable.Stream[Int] = Stream(1, ?) 

scala> lazy val s2 : Stream[Int]= Stream.cons(1, (s2, s1).zipped.map { _ + _ }) 
s2: Stream[Int] = <lazy> 

scala> s1 take 5 print 
1, 1, 1, 1, 1, empty 
scala> s2(0) 
res4: Int = 1 

scala> s2(1) 
java.lang.StackOverflowError 
     at $anonfun$s2$1$$anonfun$apply$1.apply(<console>:9) 
     at $anonfun$s2$1$$anonfun$apply$1.apply(<console>:9) 
     at scala.Tuple2$Zipped$$anonfun$map$1.apply(Tuple2.scala:62) 
     at scala.collection.immutable.Stream.foreach(Stream.scala:255) 
     at scala.Tuple2$Zipped.map(Tuple2.scala:60) 
     at $anonfun$s2$1.apply(<console>:9) 
     at $anonfun$s2$1.apply(<console>:9) 
     at scala.collection.immutable.Stream$Cons.tail(Stream.scala:556) 
     at scala.collection.immutable.Stream$Cons.tail(Stream.scala:550) 
     at scala.collection.immutable.Stream.foreach(Stream.scala:256) 
     at scala.Tuple2$Zipped.map(Tuple2.scala:60) 
     at $anonfun$s2$1.apply(<console>:9) 
     at $anonfun$s2$1.apply(<console>:9) 
     at scala.collection.immutable.Stream$Cons.tail(Stream.scala:556) 
     at scala.collection.immutable.Str... 

Я не могу понять причину переполнения стека. Поскольку потоки по своей сути ленивы, рекурсивное отображение должно работать.

Что случилось с этим сценарием?

Я использую версию Scala 2.8.0.RC2.

ответ

8

Проблема в том, что zipped не ленив - на самом деле он пытается оценить эту карту прямо там. Вы можете делать то, что хотите, с zip.

scala> val s1 = Stream.iterate(1)(identity _) 
s1: scala.collection.immutable.Stream[Int] = Stream(1, ?) 

scala> lazy val s2: Stream[Int] = Stream.cons(1, (s2 zip s1).map {s=>s._1+s._2}) 
s2: Stream[Int] = <lazy> 

scala> s2 take 5 print 
1, 2, 3, 4, 5, empty 
+1

Это http://lampsvn.epfl.ch/trac/scala/ticket/2634 –

Смежные вопросы