package day06; /** * 第 6 天:面向对象(下)—— 继承、多态、接口、抽象类 * 目标:理解 OOP 三大特性中的"继承"和"多态" * * 重点: * extends —— 单继承:子类拥有父类的属性和方法 * @Override —— 方法重写:子类用自己的实现覆盖父类方法 * 抽象类 —— 不能被 new,可以有抽象方法(留给子类实现) * 接口 —— 一组行为规范(方法签名),一个类可以实现多个接口 * 多态 —— 父类引用指向子类对象:Animal a = new Dog(); */ // ==================== 1. 抽象父类 ==================== abstract class Animal { protected String name; public Animal(String name) { this.name = name; } public String getName() { return name; } // 抽象方法:没有方法体,子类必须实现 public abstract String makeSound(); // 普通方法:有方法体,子类可以继承也可以重写 public void eat() { System.out.println(name + " 正在吃东西。"); } } // ==================== 2. 接口 ==================== interface Pet { void play(); // 接口中的方法默认是 public abstract String getBreed(); // 品种 } // ==================== 3. 子类 Dog ==================== class Dog extends Animal implements Pet { private String breed; // 品种 public Dog(String name, String breed) { super(name); // 调用父类构造方法(必须放在第一行) this.breed = breed; } @Override public String makeSound() { return "汪汪汪!"; } @Override public void play() { System.out.println(name + "(" + breed + ")兴奋地摇着尾巴,接住了飞盘!"); } @Override public String getBreed() { return breed; } @Override public void eat() { System.out.println(name + " 狼吞虎咽地吃着狗粮。"); } } // ==================== 4. 子类 Cat ==================== class Cat extends Animal implements Pet { private String breed; public Cat(String name, String breed) { super(name); this.breed = breed; } @Override public String makeSound() { return "喵喵喵~"; } @Override public void play() { System.out.println(name + "(" + breed + ")懒洋洋地拨弄着逗猫棒。"); } @Override public String getBreed() { return breed; } @Override public void eat() { System.out.println(name + " 优雅地小口吃着猫粮。"); } } // ==================== 测试类 ==================== class AnimalTest { public static void main(String[] args) { System.out.println("========== 动物继承体系演示 ==========\n"); // 1. 基本使用 Dog wangcai = new Dog("旺财", "金毛"); Cat miaomiao = new Cat("咪咪", "英短"); System.out.println("--- 各自叫 ---"); System.out.println(wangcai.getName() + ":" + wangcai.makeSound()); System.out.println(miaomiao.getName() + ":" + miaomiao.makeSound()); System.out.println("\n--- 各自吃 ---"); wangcai.eat(); miaomiao.eat(); System.out.println("\n--- 各自玩 ---"); wangcai.play(); miaomiao.play(); // 2. ★ 多态:父类引用指向子类对象 System.out.println("\n--- 多态演示 ---"); Animal[] zoo = { // Animal 类型的数组 new Dog("阿黄", "中华田园犬"), new Cat("小花", "橘猫"), new Dog("小黑", "拉布拉多") }; for (Animal a : zoo) { // 运行时决定调用哪个子类的 makeSound(动态绑定) System.out.println(a.getName() + ":" + a.makeSound()); a.eat(); } // 3. 接口引用 System.out.println("\n--- 接口多态 ---"); Pet[] pets = { wangcai, miaomiao }; for (Pet p : pets) { System.out.print(p.getBreed() + " -> "); p.play(); } } }