![](/img/trans.png)
[英]Java Terminology: Why compile-time error and not compile-time exception?
[英]Java terminology for differentiating runtime type from compile-time type
在 Java 中, Object
可以具有运行时类型(即创建时的类型)和转换类型(您已将其转换为的类型)。
我想知道这些类型的正确名称是什么。 例如
class A {
}
class B extends A {
}
A a = new B();
a 被创建为B
但它被声明为A
。 使用每个视角来引用a
类型的正确方法是什么?
我认为区分对象(在执行时存在,并且只有其执行时类型)和具有编译时类型的表达式(例如变量)很重要。
所以在这种情况下:
A a = new B();
a
是一个变量,类型为A
。 它在执行时的值是对B
类型对象的引用。
Java 语言规范使用“运行时类”(例如,为了覆盖,如第 15.12.4.4 节中所述)作为对象的类型。 在其他地方,我认为它只是使用“类型”作为表达式的类型,即编译时类型。
Java 语言规范讲述了变量的声明类型, getClass()
的 javadoc 讲述了对象的运行时类。
请注意,Java 中没有运行时类型之类的东西; List<String>
和List<Integer>
是不同的类型,但它们的实例共享相同的运行时类。
在这种情况下, A
是引用类型,而B
是实例类型
我会说你区分了变量/引用的类型和对象的类型。 在这种情况下
A a = new B();
变量/引用的类型为A
但对象的类型为B
。
变量a
的类型是A
。 没有改变,因为它是一个参考。 它恰好引用了类型B
的对象。 当您通过A
引用引用该B
对象时,您只能将其视为A
类型。
您可以稍后将其转换为更具体的类型
B b = (B)a;
并在该对象上使用B
方法。
您正在寻找的术语是Apparent Type和Actual Type 。
A a = new B();
表观类型是 A,因为编译器只知道该对象是类型 A。因此,此时您无法引用任何 B 特定方法。
实际类型为 B。您可以强制转换对象(即更改其明显类型)以访问 B 特定方法。
要确定a
是你可以使用类对象:
/*The java.lang.Object.getClass() method returns the runtime class of an object*/
System.out.println("a is object of: "+a.getClass());
例如,
如果表达式的类型是引用类型,则在编译时不一定知道被引用对象的类,甚至该值是否是对对象的引用而不是 null。 在 Java 编程语言中有几个地方,引用对象的实际类以无法从表达式的类型推断出的方式影响程序执行......
[剪辑]
可以使用
instanceof
测试类型为引用类型的表达式,以找出表达式的运行时值所引用的对象的类
因此,将上述语言应用于
A a = new B();
我们可能会说类似的话
表达式
a
的静态类型是A
,尽管a
存储的值是对运行时类B
对象的引用。
就个人而言,我以以下方式解释这两个概念(但请注意我不确定其正确性):
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.