在实现中更改上限时遇到这种奇怪的行为,但忘记在接口中更改它。我认为最后一条语句不应该编译,但它确实并返回了意外的结果。
trait SuperBase
trait Base extends SuperBase
class SuperBaseImpl extends SuperBase
trait Service {
def doWork[T <: Base : Manifest](body: T => Unit): String
def print[T <: Base : Manifest]: String
}
object ServiceImpl extends Service {
override def doWork[T <: SuperBase : Manifest](body: T => Unit): String =
print[T]
def print[T <: SuperBase : Manifest]: String =
manifest[T].runtimeClass.toString
}
val s: Service = ServiceImpl
// does not compile as expected
// s.print[SuperBaseImpl]
// returns "interface Base"
s.doWork { x: SuperBaseImpl => () }
编辑
正如@som-snytt 提到的-Xprint:typer
选项,我们可以看到编译器实际推断出的内容:
s.doWork[Base with SuperBaseImpl]
这解释了为什么我们得到“接口基础”。但是我仍然不太明白在这种情况下类型推断是如何以及为什么起作用的。