父类引用指向子类对象是Java多态的核心机制,即声明父类类型变量但以子类实例赋值(如Animal a = new Dog()),编译时看引用类型、运行时根据实际对象动态绑定重写方法,需满足继承、重写、向上转型三条件。

Java 中的多态,核心体现之一就是“父类引用指向子类对象”。这不是语法糖,而是基于继承和方法重写的运行时行为,关键在于编译看左边(引用类型),运行看右边(实际对象类型)。
什么是父类引用指向子类对象
就是声明一个父类类型的变量,但用子类的构造器创建对象并赋值给它。例如:
Animal a = new Dog(); // Animal 是父类,Dog 是子类 a.speak(); // 实际调用 Dog 类中重写的 speak() 方法
这里 a 的编译时类型是 Animal,所以只能调用 Animal 中声明过的方法;但运行时它指向的是 Dog 对象,所以真正执行的是 Dog 中重写后的方法。
必须满足的三个条件
- 有继承关系:子类 extends 父类,或实现同一接口
- 有方法重写:子类重写了父类的非 private、非 static、非 final 的实例方法
-
父类引用指向子类对象:如
Parent p = new Child();
能调用什么?不能调用什么?
父类引用只能访问父类中定义过的成员:
立即学习“Java免费学习笔记(深入)”;
- 可以调用父类中声明的方法(实际执行子类重写版本)
- 可以访问父类中 public / protected 的字段(注意:字段不具有多态性,访问的是父类中的字段)
- 不能直接调用子类独有的方法或字段 —— 编译报错
- 若需调用子类特有功能,必须向下转型:
Dog d = (Dog) a;,但要先用instanceof判断,避免ClassCastException
为什么设计成这样?有什么好处?
这种写法让程序更灵活、可扩展:
- 方法参数接收父类类型,就能传入任意子类对象,无需为每个子类写重复逻辑
- 新增子类时,只要遵循父类约定,原有使用父类引用的代码几乎不用改
- 配合集合统一管理不同子类对象,比如
List<animal> zoo = Arrays.asList(new Dog(), new Cat());</animal>


















