我有一个名为Entity
的类,它是我在整个程序中使用的许多其他对象的abstract
超类(对于此示例,Apple
类)。
在许多方法中,我通过打印打印语句的类名来打印调试语句,然后是实际的调试消息。然而,令我惊讶的是,当我从Apple
的实例调用继承的方法时,会打印Apple
的类名而不是Entity
的类名(这是方法所在的位置)实际上是位于。
要采用一个更容易发布代码段的相关示例,我已覆盖toString()
,如下所示:
public abstract class Entity {
private String name;
@Override
public String toString() {
return getClass().getSimpleName() + " " + (name != null ? name : super.hashCode());
}
}
因为我没有在Apple
类中进一步覆盖此方法,所以我希望返回的String的第一部分为Entity
,而不是Apple
。然而它返回Apple
(这对于这个用例来说这很好用,但仍然有些令人费解)。
我尝试查看Object#getClass()
的实现,但无法将其声明为native
方法。
public final native Class<?> getClass();
有人可以解释为什么会这样吗?
答案 0 :(得分:7)
您正在呼叫getClass()
。它总是返回与对象的实际执行时类型相关联的Class
对象的引用,而不是您调用它的表达式的编译时类型的类。例如:
Object foo = "this is a string";
Class<?> clazz = foo.getClass();
clazz
会引用String
的课程,而不是Object
的课程。
您无需查看getClass()
的实施 - 只需查看documentation:
表示此对象的运行时类的Class对象。
请注意“运行时”位,如“在执行时确定,而不是在编译时确定”。
在这种情况下,我认为完全在toString()
的结果中返回执行时类名称是合理的,但是如果你真的真的想要的话Entity
课程,您只需使用Entity.class
。