试试这个:
object Box {
val stuff:Any = "something"
def foo[T]():T = {
val z = stuff
println(s"z = $z class = ${z.getClass.getName}")
val y = z.asInstanceOf[T]
println(s"y = $y class = ${y.getClass.getName}")
y
}
}
println(Box.foo[Boolean]())
跑步时我得到输出:
z = something class = java.lang.String
y = something class = java.lang.String
所以即使东西是Any类型,它确实知道z(从stuff分配)是一个String。我显然试图把它转换为T,这在我的println语句中显然是布尔值。为什么这不会爆炸?为什么它认为y是一个字符串?
如果我将foo()中的T硬连接到布尔值,我会得到预期的失败输出:
z = something class = java.lang.String
Exception in thread "main" java.lang.ClassCastException: java.lang.String cannot be cast to java.lang.Boolean
at scala.runtime.BoxesRunTime.unboxToBoolean(BoxesRunTime.java:85)
...
它完全忽略了我的.asInstanceOf [T]。为什么呢?
答案 0 :(得分:1)
正如克里斯·马丁所说,这是因为类型擦除而发生的。但是在scala中,可以通过ClassTag
我稍微修改了你的代码,如果你运行它你会得到一个ClassCastException
object Box {
val stuff: Any = "something"
def foo[T](implicit ev: ClassTag[T]): T = {
val z = stuff
println(s"z = $z class = ${z.getClass.getName}")
val y = ev.runtimeClass.cast(z)
println(s"y = $y class = ${y.getClass.getName}")
z.asInstanceOf[T]
}
}
println(Box.foo[Boolean])