问题的历史:
多态是面向对象编程(OOP)的一个关键原则,自Java创建以来一直被支持。它允许对象在程序执行期间根据其实际类型表现出不同的行为,即使使用的是基类类型的引用。
问题:
如果没有多态性,代码将变得不灵活,常常会出现冗余的switch-case或if-else结构来处理不同类型的对象。这使得代码的维护和扩展变得复杂。多态性解决了为不同类型编写重复代码的必要性。
解决方案:
Java中的多态性通过继承和接口实现。它允许:
代码示例:
class Animal { void speak() { System.out.println("动物在说话"); } } class Dog extends Animal { @Override void speak() { System.out.println("狗在叫"); } } class Cat extends Animal { @Override void speak() { System.out.println("猫在喵喵叫"); } } public class PolyDemo { public static void main(String[] args) { Animal a1 = new Dog(); Animal a2 = new Cat(); a1.speak(); // 狗在叫 a2.speak(); // 猫在喵喵叫 } }
关键特性:
重载(overloading)和重写(overriding)在多态中的区别是什么?
重载是在一个类中定义多个同名但具有不同签名的方法。重写是在子类中定义与父类中相同签名的方法。
class Example { void foo(int x) {} void foo(String y) {} // 这是重载 } class Base { void foo() {} } class Child extends Base { @Override void foo() {} // 这是重写 }
没有继承可以有多态吗?
在Java的经典理解中:没有;多态性需要存在继承层次或实现的接口。
是否可以通过父类引用调用子类的方法?
只能调用在父类中定义或在子类中重写的方法。子类中仅存在的方法不能在没有类型转换的情况下被调用。
Animal a = new Dog(); a.speak(); // 可以 // a.fetch(); // 编译错误,即使Dog有fetch()方法
在项目中实现了Dog、Cat、Cow类,但所用代码直接与类型交互,通过显式转换和instanceof调用方法:
优点:
缺点:
通过虚拟的speak()继承Animal。所有交互通过基类类型Animal进行。
优点:
缺点: