这些似乎实际上是等同的:
scala> ("asd" zip "zxc").toMap
res62: scala.collection.immutable.Map[Char,Char] = Map(a -> z, s -> x, d -> c)
scala> Map(("asd" zip "zxc"): _*)
res63: scala.collection.immutable.Map[Char,Char] = Map(a -> z, s -> x, d -> c)
然而,现实生活中的差异是什么?哪一个比较惯用?运行时性能会有所不同吗?
我确信同样/类似的问题可能会被问到其他类似的结构对,所以请随意给出更一般/抽象的答案:)
答案 0 :(得分:3)
两者之间存在真正的差异,因为 这些方法已定义:
apply
构造函数是在目标集合的伴侣中定义的:
object Coll {
def apply[T](els: T*): Coll[T] = ???
}
这意味着除了Seq
元素之外,它绝对没有关于输入的信息,因此它只是遍历该序列并构建Coll
。
另一方面,toSeq
,toArray
,...在 source 集合中定义,这意味着他们拥有关于其内部的所有额外信息
通常,您可以依靠toXXX
方法在需要时进行短路,或者返回一些有意义的专门收藏。
作为一个愚蠢的例子,请考虑:
List(1,2,3).toSeq // toSeq returns `this`, there is no overhead
// vs.
Seq(List(1,2,3): _*) // this will copy that list into a new one...
如果用Stream.continually(1)
...
答案 1 :(得分:0)
我个人更喜欢第一个变体,因为它更清晰可读。两者在性能或其他特征上没有实际差异。在第一种情况下,你创建一个索引seq,然后在第二种情况下将它转换为map,你使用这个seq提取器sintax :_*
这是Scala最好的部分。就像Odersky教授告诉许多人一样,Scala设计的一部分是为不同的问题提供制作设计解决方案。所以在这种情况下,你可以选择任何。但正如我告诉你的第一个更清晰易懂,将核心符号编程留给Scalaz
=)