Я новичок в Scala и пытаюсь обернуть голову вокруг продолжений
Я пытаюсь воспроизвести оператор yield return
С#.
Следуя этому сообщению, я написал следующий код:
package com.company.scalatest
import scala.util.continuations._;
object GenTest {
val gen = new Generator[Int] {
def produce = {
yieldValue(1)
yieldValue(2)
yieldValue(3)
yieldValue(42)
}
}
// Does not compile :(
// val gen2 = new Generator[Int] {
// def produce = {
// var ints = List(1, 2, 3, 42);
//
// ints.foreach((theInt) => yieldValue(theInt));
// }
// }
// But this works?
val gen3 = new Generator[Int] {
def produce = {
var ints = List(1, 2, 3, 42);
var i = 0;
while (i < ints.length) {
yieldValue(ints(i));
i = i + 1;
}
}
}
def main(args: Array[String]): Unit = {
gen.foreach(println);
// gen2.foreach(println);
gen3.foreach(println);
}
}
abstract class Generator[E] {
var loopFn: (E => Unit) = null
def produce(): Unit @cps[Unit]
def foreach(f: => (E => Unit)): Unit = {
loopFn = f
reset[Unit, Unit](produce)
}
def yieldValue(value: E) =
shift { genK: (Unit => Unit) =>
loopFn(value)
genK(())
()
}
}
Как вы можете видеть, gen2
закомментирован, поскольку он не компилируется. Поскольку я могу легко перебирать содержимое списка, используя цикл while (см. gen3
), я ожидал, что цикл foreach будет работать так же хорошо.
Ошибка компиляции:
no type parameters for method foreach: (f: Int => B)Unit exist so that
it can be applied to arguments (Int => Unit @scala.util.continuations.cpsParam[Unit,Unit])
--- because ---
argument expression type is not compatible with formal parameter type;
found : Int => Unit @scala.util.continuations.cpsParam[Unit,Unit]
required: Int => ?B
Почему я получаю эту ошибку и есть способ обойти это с чем-то более чистым, чем цикл while?
Спасибо