【问题标题】:Does scala collection's flatten keep order?scala 集合的 flatten 是否保持秩序?
【发布时间】:2018-11-08 11:02:59
【问题描述】:

我查看了 flatten 的documentation,该示例似乎表明结果中元素的顺序保持了输入的顺序。是否有我们可以参考的文档或源代码来确保情况如此?或者,“将这个可遍历集合的集合转换为由这些可遍历集合的元素形成的集合”的文档是否足以证实这一点?

更新:我最初的问题不够清楚。我想问一下内部维护顺序的集合(如 List),我们在 flatten() 中使用默认的隐式遍历。 prayagupd 已经回答了这个问题。

【问题讨论】:

    标签: scala


    【解决方案1】:

    如果您阅读scala 2.12.xflatten function,您可以看到它按顺序将给定的输入添加到新集合中。

      //a sequential view of the collection
      private def sequential: TraversableOnce[A] = this.asInstanceOf[GenTraversableOnce[A]].seq
    
      def flatten[B](implicit asTraversable: A => /*<:<!!!*/ GenTraversableOnce[B]): CC[B] = {
        val b = genericBuilder[B]
        for (xs <- sequential)
          b ++= asTraversable(xs).seq
        b.result()
      }
    

    你也可以用例子来验证,

    scala> List(List("order1", "order2"), List("order10", "order11")).flatten
    res1: List[String] = List(order1, order2, order10, order11)
    

    即使您提供自己的可遍历,顺序也保持不变,

    scala> val asTraversable: List[String] => List[String] = list => list.map(elem => s"mutated $elem")
    asTraversable: List[String] => List[String] = $$Lambda$1271/1988351538@513bec8c
    
    scala> List(List("order1", "order2"), List("order10", "order11")).flatten(asTraversable)
    res2: List[String] = List(mutated order1, mutated order2, mutated order10, mutated order11)
    

    注意:以上仅适用于维护顺序的底层数据结构。 比如Set不维护秩序

    scala> Set(1, 2, 3, 4, 5, 6, 7, 8, 9, 10).seq
    res3: scala.collection.immutable.Set[Int] = Set(5, 10, 1, 6, 9, 2, 7, 3, 8, 4)
    

    【讨论】:

    • 有一个重大例外:SetTraversable,并且不会保留顺序(一旦超过 4 个元素)。
    猜你喜欢
    • 2017-12-23
    • 2017-10-19
    • 2014-07-14
    • 1970-01-01
    • 1970-01-01
    • 2013-07-22
    • 1970-01-01
    • 2014-11-05
    • 2017-05-29
    相关资源
    最近更新 更多