我正在将一些代码从Scala迁移到Kotlin,我观察到不同的行为:
Scala:
var i = 0
Iterator.continually{
println(s"i=$i")
i += 1
i
}.takeWhile {
_ < 3
}.foreach { i =>
println(s"I=$i")
}
字符串
输出量:
i=0
I=1
i=1
I=2
i=2
型
Kotlin等价物:
fun <A> continousIterator(func: () -> A): Iterable<A> =
object: Iterable<A> {
override fun iterator() =
object: Iterator<A> {
override fun hasNext(): Boolean = true
override fun next(): A = func()
}
}
var i = 0;
fun main() {
continousIterator{
println("i=$i")
i += 1
i
}.takeWhile{
it < 3
}.forEach {
println("I=$it")
}
}
型
输出量:
i=0
i=1
i=2
I=1
I=2
型
当我们有状态时,结果是不一样的,func()
和iterator
的调用顺序是不同的。
我想知道为什么。
1条答案
按热度按时间shyt4zoc1#
在Kotlin中,当
takeWhile
被调用时,takeWhile
立即遍历序列并打印0到2,并生成List
。只有在此之后,forEach
才会运行,打印1和2。要复制Scala的行为,你需要
forEach
来消费序列,而不是takeWhile
。Sequence
可以做到这一点:字符串
Sequence
上的操作都是惰性的,除非绝对必要,否则它们不会使用序列。