我正在学习Scala并对下限有疑问。
我有一个班级:
class Queue[+T] {
def enqueue[U>:T](x : U) = new Queue[U]()
}
class Fruit
class Apple extends Fruit
class Orange extends Fruit
class Another
我发现,对于任何类型的队列,例如:
val q1 = new Queue[Fruit]
以下所有三行都将通过编译
q1.enqueue(new Apple)
q1.enqueue(new Orange)
q1.enqueue(new Another)
我的问题是:如果我们使用下限来定义U必须是超类型的T,在上面的行中,Apple显然不是超类型的Fruit,它怎么能传递给enqueue函数?
“另一个”类根本不在水果层中,它如何在入队函数中使用?
请帮我解决这个问题。
此致 凯文
答案 0 :(得分:12)
如果你看一下新队列的回归:
scala> q1.enqueue(new Apple)
res0: Queue[Fruit] = Queue@17892d5
scala> q1.enqueue(new Orange)
res1: Queue[Fruit] = Queue@bdec44
scala> q1.enqueue(new Another)
res2: Queue[ScalaObject] = Queue@104bce3
你所说的具体U应该是超级型的T(或T)。这意味着另一个很好用,因为ScalaObject是Another和Fruit中最具体的超类型。
答案 1 :(得分:5)
我的问题是:如果我们使用下限来定义U必须是超类型的T,在上面的行中,Apple显然不是超类型的Fruit,它怎么能传递给enqueue函数?
但new Apple
是Fruit
,而Fruit
是Fruit
的超类型。因此,在您的情况下,U
为Fruit
,并返回Queue[Fruit]
。 new Another
是ScalaObject
,也是Fruit
的超类型...