【问题标题】:What is the type of a variable-length argument list in Scala?Scala 中可变长度参数列表的类型是什么?
【发布时间】:2012-11-03 18:50:48
【问题描述】:

假设我声明一个函数如下:

def test(args: String*) = args mkString

args的类型是什么?

【问题讨论】:

    标签: scala variadic-functions


    【解决方案1】:

    这称为可变数量的参数或简称为可变参数。它的静态类型是Seq[T],其中T 代表T*。因为Seq[T] 是一个接口,所以它不能用作实现,在这种情况下是scala.collection.mutable.WrappedArray[T]。要找出这些东西,使用 REPL 会很有用:

    // static type
    scala> def test(args: String*) = args
    test: (args: String*)Seq[String]
    
    // runtime type
    scala> def test(args: String*) = args.getClass.getName
    test: (args: String*)String
    
    scala> test("")
    res2: String = scala.collection.mutable.WrappedArray$ofRef
    

    可变参数通常与_* 符号结合使用,这是对编译器将Seq[T] 的元素而不是序列本身传递给函数的提示:

    scala> def test[T](seq: T*) = seq
    test: [T](seq: T*)Seq[T]
    
    // result contains the sequence
    scala> test(Seq(1,2,3))
    res3: Seq[Seq[Int]] = WrappedArray(List(1, 2, 3))
    
    // result contains elements of the sequence
    scala> test(Seq(1,2,3): _*)
    res4: Seq[Int] = List(1, 2, 3)
    

    【讨论】:

    • 是的,这有一个有趣的效果,你不能立即传递 var-len 参数,def f1(args: Int*) = args.length; def f2(args: Int*) = f1(args)。它将在 f2 定义中给出found Seq[Int] whereas Int is required mismatch error。要规避,您需要def f2 = f1(args: _*)。所以,编译器认为参数是一个单一的值和序列,在编译时:)
    • 从 Scala 2.13.6 开始,使用的 Seq 的实现是 scala.collection.immutable.ArraySeq
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-01-13
    • 2018-03-10
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多