10

我写了一个方法,它接受 Seq[String] 的所有子类的对象。不幸的是,它不接受 Array[String] 类型的对象。Array[String] 不是 Seq[String] 的子类吗?

scala> def test[T <: Seq[String]](x: T) = {}
test: [T <: Seq[String]](x: T)Unit

scala> val data = "This is a test string"
data: java.lang.String = This is a test string

scala> test(data.split(" "))
<console>:10: error: inferred type arguments [Array[java.lang.String]] do not conform to method test's type parameter bounds [T <: Seq[String]]
              test(data.split(" "))
4

2 回答 2

11

不,Array[String]转换为常规 JVM 数组,就像您在 Java 中看到的那样:String[].

Array[String]您看到在其他 Scala集合上看到的所有操作的原因Seq是存在从to的隐式转换Array[T]ArrayOps[T]

做这个:

def test[T <% Seq[String]](x: T) = {}

这称为视图绑定。这意味着它T应该是 的子类型,Seq[String]或者应该存在范围内的隐式转换,该转换转换TSeq[String]. 在幕后,编译器实际上给 增加了一个隐式参数test,所以这个方法就变成了:

scala> def test[T <% Seq[String]](x: T) = {}
test: [T](x: T)(implicit evidence$1: T => Seq[String])Unit

implicit evidence$1是现在充当方法主体内的T隐式转换的函数。Seq[String]

于 2012-07-17T13:04:42.607 回答
5

源(或API 文档)状态,Array定义为

final class Array[T] extends Serializable with Cloneable

也就是说,它不是 的子类型Seq。但是,文档还提到了一个隐式转换WrappedArray,后者是Seq.

于 2012-07-17T13:09:25.867 回答