Skip to content

多态条件

多态让「同一个操作,不同的结果」成为可能。但多态不是凭空出现的,它需要满足三个条件。

三个条件缺一不可

┌─────────────────────────────────────────────────────────────┐
│                   多态的三个条件                              │
├─────────────────────────────────────────────────────────────┤
│                                                             │
│  1. 继承/实现关系                                           │
│     子类继承父类,或实现接口                                   │
│                                                             │
│  2. 方法重写                                                │
│     子类重写父类的方法                                         │
│                                                             │
│  3. 向上转型                                                │
│     父类引用指向子类对象                                        │
│                                                             │
└─────────────────────────────────────────────────────────────┘

代码示例

三个条件

java
public class PolyConditionDemo {

    // 条件1:父类
    static class Shape {
        void draw() {
            System.out.println("Drawing shape");
        }
    }

    // 条件2:子类 - 重写方法
    static class Circle extends Shape {
        @Override
        void draw() {
            System.out.println("Drawing circle");
        }
    }

    static class Rectangle extends Shape {
        @Override
        void draw() {
            System.out.println("Drawing rectangle");
        }
    }

    // 条件3:父类引用指向子类对象
    public static void main(String[] args) {
        Shape s1 = new Circle();    // 向上转型
        Shape s2 = new Rectangle(); // 向上转型

        // 调用的是实际对象的方法
        s1.draw(); // Drawing circle
        s2.draw(); // Drawing rectangle
    }
}

条件验证

java
public class ConditionVerificationDemo {

    static class Parent {
        void method() {
            System.out.println("Parent method");
        }
    }

    static class Child extends Parent {
        @Override
        void method() {
            System.out.println("Child method");
        }

        void childMethod() {
            System.out.println("Child only method");
        }
    }

    public static void main(String[] args) {
        Parent obj = new Child();

        // ✅ 满足多态条件
        obj.method(); // 调用 Child 的方法

        // ❌ 不满足:父类引用不能调用子类特有方法
        // obj.childMethod(); // 编译错误
    }
}

缺一不可

java
public class AllConditionsDemo {

    // ❌ 缺少继承 - 无法多态
    class A {
        void test() {}
    }
    class B {
        void test() {} // 没有继承 A
    }

    // ❌ 缺少重写 - 不是多态
    class C extends A {
        // 没有重写 test()
        void test2() {}
    }

    // ✅ 满足所有条件
    class D extends A {
        @Override
        void test() {}
    }
}

常见误区

误区 1:重载算多态吗?

不算。重载是编译时多态(静态绑定),严格意义上的多态指的是运行时多态。

java
class Parent {
    void display(int x) { }  // 重载
}
class Child extends Parent {
    void display(String s) { }  // 重载,不是重写
}

误区 2:没有继承就没有多态

接口也可以实现多态,本质上是一样的:

java
interface Drawable {
    void draw();
}

class Circle implements Drawable {
    @Override
    public void draw() {
        System.out.println("Drawing circle");
    }
}

class Square implements Drawable {
    @Override
    public void draw() {
        System.out.println("Drawing square");
    }
}

// 仍然满足三个条件:
// 1. 实现关系
// 2. 方法重写
// 3. 向上转型
public static void main(String[] args) {
    Drawable d1 = new Circle();
    Drawable d2 = new Square();
    d1.draw(); // Drawing circle
    d2.draw(); // Drawing square
}

总结

多态三要素:
继承/实现 → 方法重写 → 向上转型
   ↓            ↓          ↓
 是谁的儿子   做自己的事   被当父亲用

记住:没有继承就没有多态,没有重写就没有多态,没有父类引用就没有多态

基于 VitePress 构建