【问题标题】:Scala - iterators and takeWhileScala - 迭代器和 takeWhile
【发布时间】:2013-04-27 17:43:03
【问题描述】:

我正在运行以下代码:

 val it = List(1,1,1,2,2,3,3).iterator.buffered
 val compare = it.head
it.takeWhile(_ == compare).toList

它返回 (1,1,1)。但是,如果我将其运行为:

val it = List(1,1,1,2,2,3,3).iterator.buffered
it.takeWhile(_ == it.head).toList

我得到 (1,1)。为什么会这样? head 不是在调用takeWhile 时评估的,结果应该相同吗?

【问题讨论】:

    标签: scala iterator


    【解决方案1】:

    因为迭代器是可变的,it.head 的值取决于它的计算时间。

    检查implementation of takeWhile 发现它在应用谓词之前删除了迭代器的头部。

    因此,在第三次迭代中,从谓词中评估的it.head 将是2,因为第三个元素已被删除。

    这说明了为什么您应该更喜欢不变性。它排除了一整类这样的非显而易见的行为。

    【讨论】:

      【解决方案2】:

      添加到上面的@Ben James 答案。下面是takeWhile方法代码(学分:ben):

      def hasNext = hdDefined || tail.hasNext && {
        hd = tail.next() //line 2
        if (p(hd)) hdDefined = true
        else tail = Iterator.empty
        hdDefined
      }
      

      在第 2 行之后的第三次迭代中,值为:hd=1,剩余的迭代器为List(2,2,3,3)。在调用p(hd) 时,它会检查迭代器的head,在本例中为2。因此它坏了。

      【讨论】:

        猜你喜欢
        • 2013-07-16
        • 2015-02-08
        • 1970-01-01
        • 2012-03-08
        • 1970-01-01
        • 2011-06-20
        • 2021-07-01
        • 2019-01-06
        • 2012-01-28
        相关资源
        最近更新 更多