29

假设,我们有:

class B
class A extends B
trait T

然后它成立:

val a: A with T = new A with T 
a.isInstanceOf[B]  // result is true !

是否可以说,该isInstanceOf方法检查是否至少有一种类型(不是所有类型)与子类型关系中的右侧匹配?

乍一看,我认为带有 type 的值A with T不能是 的子类型B,因为A T不是 的子类型B。但它是A 或者 T是一个子类型B——对吗?

4

2 回答 2

39

isInstanceOf查看继承链中是否有相应的条目。A with T包含AB的链必须为真Ta.isInstanceOf[B]

编辑:

实际上生成的字节码调用 javas instanceof,所以它会a instanceof B在 java.xml 中。更复杂一点的调用a.isInstanceOf[A with T]就像(a instanceof A) && (a instanceof T).

于 2012-07-02T08:35:51.407 回答
13

乍一看,我认为类型 A 和 T 的值不能是 B 的子类型

这里有两个误解。首先,实例的静态类型对结果有任何影响isInstanceOf:没有。需要明确的是,在做的时候, typea.isInstanceOf[B]的事实是不相关的。aA with T

该方法isInstanceOf由 JVM 在字节码级别实现。它查看每个实例携带的类信息,并检查是B类之一(实例本身及其祖先的类)还是实现的接口之一。这就是“is-a”关系:“a is a B”。

从技术上讲,isInstanceOf它是 Java 反射的一部分,它被称为instanceof.

第二个误解是继承可以以某种方式删除父类型。这永远不会发生:继承只添加类型,从不删除它们。类型A with T是 an A, a B, a T, anAnyVal和 an Any。因此,即使isInstanceOf确实查看了 type A with T,它仍然会返回 true。

于 2012-07-02T13:58:49.710 回答