好吧,你可以声明引用s1
属于类型Graduate
。通过声明引用获得的主要好处super type
,是多态性.
通过超类型引用,指向子类对象,可以将同一个引用绑定到多个子类对象。实际调用的方法将在运行时根据指向的对象决定。但是,实现这一点的主要条件是,该方法也应该在子类中定义,否则compiler将无法找到方法声明。
在这里,你被迫downcast
,因为您尚未在超类中定义该方法。由于编译器无法看到该方法的定义Student
班级。它不知道实际对象是什么s1
指着。请记住,编译器仅检查引用类型来查找方法声明。
一般来说,每当您看到自己在代码中向下转换为子类时,这几乎总是一个错误的迹象(但也有一些例外)。你应该修改你的课程。
让我们看看使用超类引用而不是子类引用可以获得什么好处:
例如:假设你有另一个子类Student
as:
class Phd extends Student {
getResearchTopic(){...}
}
并且您还提供了一个定义(默认定义)Student
class:
class Student {
getResearchTopic(){...}
}
现在,您创建以下两个对象,它们都由Student
参考:
Student student = new Phd();
student.getResearchTopic(); // Calls Phd class method
student = new Graduate();
student.getResearchTopic(); // Calls Graduate class method
因此,只需一个引用,您就可以访问特定于子类的方法。
您可以在以下位置看到此功能的一个主要实现factory method
模式,其中单个静态方法根据某些条件返回不同子类的对象:
public static Student getInstance(String type) {
if (type.equals("graduate"))
return new Graduate();
else if (type.equals("phd"))
return new Phd();
}
所以,你可以看到同一个方法返回不同子类的对象。
您可以做的所有上述事情都只是因为一个概念:
超类引用可以引用任何子类对象,但反之则不然.