当前位置: 首页 > news >正文

【从零开始学习JAVA | 第四篇】继承与多态

前言

上一篇我们掌握了面向对象的基础——类与对象、封装。本篇继续深入,学习面向对象三大特性中的另外两个:继承多态

这两个特性是 Java 实现代码复用、灵活扩展的核心机制,也是面试中最高频的考点之一,务必认真学习。


一、继承

1.1 什么是继承?

继承允许一个类获取另一个类的属性和方法,避免重复代码。

  • 被继承的类叫父类(超类)
  • 继承的类叫子类
  • 使用关键字extends
graph TD A[Animal 父类] --> B[Dog 子类] A --> C[Cat 子类] A --> D[Bird 子类] style A fill:#cce5ff style B fill:#d4edda style C fill:#d4edda style D fill:#d4edda

💡 生活类比:父亲有房子和车,儿子继承后直接拥有,不需要自己再买。

1.2 继承的基本写法

不使用继承时,存在大量重复代码:

// 重复定义相同属性和方法 ❌ public class Dog { String name; int age; public void eat() { System.out.println(name + " 在吃饭"); } public void bark() { System.out.println("汪汪汪"); } } public class Cat { String name; int age; public void eat() { System.out.println(name + " 在吃饭"); } public void meow() { System.out.println("喵喵喵"); } }

使用继承后,公共部分抽取到父类:

// 父类 public class Animal { String name; int age; public void eat() { System.out.println(name + " 在吃饭"); } } // 子类 Dog public class Dog extends Animal { public void bark() { System.out.println(name + " 说:汪汪汪"); } } // 子类 Cat public class Cat extends Animal { public void meow() { System.out.println(name + " 说:喵喵喵"); } }
public class Demo { public static void main(String[] args) { Dog dog = new Dog(); dog.name = "旺财"; dog.age = 3; dog.eat(); // 继承自父类 dog.bark(); // 自己的方法 Cat cat = new Cat(); cat.name = "咪咪"; cat.eat(); cat.meow(); } }

输出结果:

旺财 在吃饭 旺财 说:汪汪汪 咪咪 在吃饭 咪咪 说:喵喵喵

1.3 继承的特点

  • Java 只支持单继承,一个类只能有一个直接父类
  • 但支持多层继承:A → B → C
  • 所有类默认继承Object类(Java 的祖宗类)
graph TD A[Object] --> B[Animal] B --> C[Dog] C --> D[导盲犬 GuideDoc] style A fill:#ffe0cc style B fill:#cce5ff style C fill:#d4edda style D fill:#fff3cd

1.4 子类能继承什么?

父类成员能否继承
public 属性/方法✅ 可以
protected 属性/方法✅ 可以
默认(不写修饰符)✅ 同包可以
private 属性/方法❌ 不能直接访问
构造方法❌ 不能继承,但可以调用

二、super 关键字

super代表父类对象,用于访问父类的属性、方法和构造方法。

2.1 调用父类构造方法

public class Animal { private String name; private int age; public Animal(String name, int age) { this.name = name; this.age = age; } public String getName() { return name; } }
public class Dog extends Animal { private String breed; // 品种 public Dog(String name, int age, String breed) { super(name, age); // 必须在第一行,调用父类构造 this.breed = breed; } public void printInfo() { System.out.println("名字:" + getName() + ",品种:" + breed); } }
Dog dog = new Dog("旺财", 3, "拉布拉多"); dog.printInfo(); // 名字:旺财,品种:拉布拉多

2.2 this 与 super 对比

thissuper
代表当前对象父类对象
访问属性this.属性super.属性
调用方法this.方法()super.方法()
调用构造this()super()
位置要求构造方法第一行构造方法第一行

⚠️this()super()不能同时出现在构造方法中。


三、方法重写(Override)

方法重写:子类对父类继承来的方法进行重新定义,覆盖原有实现。

3.1 重写规则

  • 方法名、参数列表必须完全相同
  • 返回值类型相同或是其子类
  • 访问权限不能更严格(可以更宽松)
  • 建议加@Override注解,让编译器帮助检查
public class Animal { public void speak() { System.out.println("动物在叫..."); } } public class Dog extends Animal { @Override public void speak() { System.out.println("汪汪汪!"); } } public class Cat extends Animal { @Override public void speak() { System.out.println("喵喵喵!"); } }
public class Demo { public static void main(String[] args) { Animal a = new Animal(); Dog d = new Dog(); Cat c = new Cat(); a.speak(); // 动物在叫... d.speak(); // 汪汪汪! c.speak(); // 喵喵喵! } }

3.2 重写 vs 重载

方法重载(Overload)方法重写(Override)
位置同一个类父子类之间
方法名相同相同
参数列表必须不同必须相同
返回值无要求必须相同或子类

四、多态

4.1 什么是多态?

多态:同一种行为,不同对象表现出不同的形态。

核心口诀:父类引用指向子类对象

Animal a = new Dog(); // 父类类型的变量,指向子类对象
graph LR A[Animal类型的引用] -->|指向| B[Dog对象] A -->|指向| C[Cat对象] A -->|指向| D[Bird对象] style A fill:#cce5ff

4.2 多态的完整示例

public class Animal { private String name; public Animal(String name) { this.name = name; } public String getName() { return name; } public void speak() { System.out.println("动物在叫"); } } public class Dog extends Animal { public Dog(String name) { super(name); } @Override public void speak() { System.out.println(getName() + " 说:汪汪汪!"); } } public class Cat extends Animal { public Cat(String name) { super(name); } @Override public void speak() { System.out.println(getName() + " 说:喵喵喵!"); } }
public class Demo { public static void main(String[] args) { // 父类引用指向不同子类对象 Animal a1 = new Dog("旺财"); Animal a2 = new Cat("咪咪"); Animal a3 = new Dog("小黑"); // 同一方法,不同表现 a1.speak(); a2.speak(); a3.speak(); } }

输出结果:

旺财 说:汪汪汪! 咪咪 说:喵喵喵! 小黑 说:汪汪汪!

4.3 多态的最大好处

多态让方法可以接收任意子类对象,极大提升代码灵活性:

public class Demo { // 只需写一个方法,传入任何 Animal 子类都能正确执行 public static void letSpeak(Animal animal) { animal.speak(); } public static void main(String[] args) { letSpeak(new Dog("旺财")); letSpeak(new Cat("咪咪")); } }

💡 以后新增Bird类,letSpeak方法无需改动,直接传入即可。这就是多态的威力。

4.4 多态的弊端与类型转换

使用父类引用时,只能调用父类中定义的方法,无法调用子类独有方法。

Animal a = new Dog("旺财"); a.speak(); // ✅ 可以,Animal 中有 speak a.bark(); // ❌ 报错,Animal 中没有 bark

需要调用子类独有方法时,要进行向下转型

Animal a = new Dog("旺财"); // 向下转型前,先用 instanceof 判断类型 if (a instanceof Dog) { Dog d = (Dog) a; // 强制转换 d.bark(); // ✅ 现在可以调用了 }
graph TD A[向上转型] -->|自动, 安全| B["Animal a = new Dog()"] C[向下转型] -->|强制, 需判断| D["Dog d = (Dog) a"] D --> E{instanceof 检查} E -->|是 Dog| F[✅ 转换成功] E -->|不是 Dog| G[❌ ClassCastException] style F fill:#d4edda style G fill:#f8d7da

五、final 关键字

final表示"最终的、不可改变的",可以修饰类、方法、变量。

修饰对象含义
final不能被继承(如 String 类)
final方法不能被重写
final变量变为常量,不能重新赋值
// final 类,不能被继承 public final class MathUtil { } public class Animal { // final 方法,不能被重写 public final void breathe() { System.out.println("呼吸"); } } public class Demo { public static void main(String[] args) { // final 变量,相当于常量 final double PI = 3.14159; // PI = 3.14; // ❌ 报错,不能修改 System.out.println(PI); } }

六、综合练习

题目:定义员工体系,公司有普通员工和经理,都有姓名和工资,但经理还有奖金,且工作内容不同。

// 父类 public class Employee { private String name; private double salary; public Employee(String name, double salary) { this.name = name; this.salary = salary; } public String getName() { return name; } public double getSalary() { return salary; } public void work() { System.out.println(name + " 正在工作"); } public void printSalary() { System.out.println(name + " 的薪资:¥" + salary); } }
// 普通员工 public class Worker extends Employee { public Worker(String name, double salary) { super(name, salary); } @Override public void work() { System.out.println(getName() + " 正在努力搬砖 🧱"); } }
// 经理 public class Manager extends Employee { private double bonus; public Manager(String name, double salary, double bonus) { super(name, salary); this.bonus = bonus; } @Override public void work() { System.out.println(getName() + " 正在开会讨论方案 📊"); } @Override public void printSalary() { System.out.println(getName() + " 的薪资:¥" + getSalary() + ",奖金:¥" + bonus); } }
public class Demo { public static void main(String[] args) { Employee[] staff = { new Worker("小明", 8000), new Worker("小红", 9000), new Manager("王总", 20000, 50000) }; for (Employee e : staff) { e.work(); e.printSalary(); System.out.println("------"); } } }

输出结果:

小明 正在努力搬砖 🧱 小明 的薪资:¥8000.0 ------ 小红 正在努力搬砖 🧱 小红 的薪资:¥9000.0 ------ 王总 正在开会讨论方案 📊 王总 的薪资:¥20000.0,奖金:¥50000.0 ------

总结

graph TD A[继承与多态] --> B[继承 extends] A --> C[多态] B --> B1[代码复用] B --> B2[super关键字] B --> B3[方法重写 Override] C --> C1[父类引用指向子类对象] C --> C2[向上转型 - 自动] C --> C3[向下转型 - 强制+instanceof] C --> C4[多态的好处: 统一处理不同子类] A --> D[final关键字] D --> D1[final类不能继承] D --> D2[final方法不能重写] D --> D3[final变量是常量]
知识点核心要点
继承extends,子类拥有父类非private成员
super代表父类,调用父类构造必须在第一行
方法重写方法名参数相同,子类覆盖父类实现
多态父类引用指向子类对象,运行时动态绑定
类型转换向上自动,向下强转,转前用instanceof判断
final修饰类/方法/变量,表示不可变

写在最后

本篇是「从零开始学习JAVA」系列的第四篇,完整介绍了继承与多态的核心概念和实际应用。

继承减少了重复代码,多态让程序更灵活、更易扩展,二者结合是 Java 面向对象设计的精髓。建议把综合练习完整敲一遍,感受多态带来的便利。

如果觉得本文对你有帮助,欢迎点赞 👍 收藏 ⭐ 关注,我们下一篇见!

下一篇预告:【从零开始学习JAVA | 第五篇】抽象类与接口

http://www.jsqmd.com/news/847694/

相关文章:

  • NotebookLM文化遗产研究落地全链路(从敦煌写本到AI知识库的9步工业化流程)
  • 5分钟掌握抖音无水印批量下载:免费工具完整使用指南
  • 实时AI推理优化:如何提升模型响应速度
  • 统信UOS 20专业版图形化配置代理保姆级教程,内网访问外网就这么简单
  • 银河麒麟V10SP3-arm版本安装oracle19C数据库
  • 通过taotoken cli在ubuntu上一键配置多个开发工具环境
  • Whisky终极指南:在macOS上免费运行Windows程序的完整解决方案
  • Qt 动画进阶:手把手教你用 QCharts 可视化调试 QEasingCurve 曲线
  • Linux 网络内核参数调优完全指南
  • vert-harmonium
  • Windows右键菜单终极清理指南:5分钟快速整理你的右键菜单
  • 如何利用QuPath实现专业级数字病理分析:从入门到精通的完整指南
  • 庆阳足金回收银手镯回收PT990铂金回收钻石戒指回收旧首饰回收高价多少钱一克同城价格查询上门上门估价闲置变现转让靠谱权威排行榜 - 检测回收中心
  • Python新手避坑:明明pip install了python-dotenv,为啥还是报错找不到模块?
  • 南宁投资金条回收上门回收白银上门铂金回收旧钻石回收周边金银回收本地排名正规门店专业推荐哪家靠谱二手哪家强 - 检测回收中心
  • 别再只改属性个数了!深入PHP GC机制,用fast-destruct和变量引用优雅绕过__wakeup
  • 广州小程序定制开发公司排行 性价比维度实测对比 - 奔跑123
  • 如何通过cursor-free-vip工具扩展Cursor AI编辑器功能:完整指南与实用技巧
  • 如何从丢失的Android手机中恢复联系人
  • UBX-M9140-KB-C1100A米级定位精度,支持四星座 GNSS‌,
  • API 密钥泄露频发?OpenClaw 在企业安全治理中实现密钥轮换自动化(3 步配置)
  • 终极指南:一键安装Windows包管理器Winget的完整解决方案
  • 临沧足金回收银手镯回收PT990铂金回收钻石戒指回收旧首饰回收本地排名正规门店专业推荐哪家靠谱二手哪家强 - 检测回收中心
  • 多模态记忆:文本+文件+链接统一管理
  • 号易最高代理邀请码是多少?88000,填写注册一级代理合伙人赚的多 - 流量卡代理招商
  • 安卓平板Camera调试实录:搞定Sensor镜像翻转,让24色卡标定一次成功
  • JetBrains IDE试用期重置终极指南:30天免费使用的最佳解决方案
  • 临沧足金回收银手镯回收PT990铂金回收钻石戒指回收旧首饰回收高价多少钱一克同城价格查询上门上门估价闲置变现转让靠谱权威排行榜 - 检测回收中心
  • 大一开始迷茫?这篇长期主义技能清单比鸡汤管用
  • 51单片机中断机制详解:从原理到实战应用