学习java37天

Java 继承 (Inheritance)

继承是面向对象三大特性(封装、继承、多态)之一。它是一种代码复用 和类关系建模的机制。

一、继承的基本概念

  • 定义 :Java使用 extends 关键字建立类与类之间的继承关系。

  • 语法:

    java

    复制代码
    public class 子类 extends 父类 {
        // 子类特有的属性和方法
    }
  • 术语:

    • 子类 (Subclass):也叫派生类。继承的类。

    • 父类 (Superclass):也叫超类、基类。被继承的类。

  • 目的:

    1. 代码复用:将多个子类共有的属性和行为抽取到父类中,避免代码重复。

    2. 功能扩展:子类在继承父类功能的基础上,可以添加自己特有的功能。

    3. 建立"is-a"关系 :继承代表一种"子类是父类的一种"的逻辑关系(例如:Student is a Person)。

二、何时使用继承?

必须同时满足以下两个条件:

  1. 存在共性内容:多个类之间存在大量相同的属性或方法。

  2. 逻辑关系成立 :在逻辑上满足 "子类是父类的一种" 的关系。不能仅仅为了复用代码而滥用继承。

三、继承的特点

  1. 单继承 :Java只支持单继承,一个类只能有一个直接父类。

  2. 不支持多继承 :一个类不能同时 extends 多个父类。(但可以通过接口实现类似功能)。

  3. 支持多层继承:继承可以传递(A继承B,B继承C)。

    java

    复制代码
    class A extends B {} // A的直接父类是B
    class B extends C {} // B的直接父类是C
    // 最终,A间接继承了C。
  4. 所有类的根 :在Java中,每个类都直接或间接继承自 java.lang.Object 类(Object 类是所有类的超类)。

四、继承中成员的访问特点

1. 成员变量访问

遵循 "就近原则"。

  • 查找顺序 :局部变量 → 子类成员变量 (this) → 父类成员变量 (super)。

  • 关键字:

    • this.变量名:明确指定访问本类的成员变量。

    • super.变量名:明确指定访问父类的成员变量。

示例:

java

复制代码
class Person {
    String name = "PersonName";
}
class Student extends Person {
    String name = "StudentName";
    
    public void show(String name) {
        System.out.println(name);        // 局部变量,就近原则
        System.out.println(this.name);   // 子类的成员变量 "StudentName"
        System.out.println(super.name);  // 父类的成员变量 "PersonName"
    }
}
2. 成员方法访问

访问规则与成员变量相同(就近原则)。关键在于方法的重写 (Override)。

五、方法的重写 (Override)

1. 定义与时机
  • 定义 :在继承体系中,子类 出现了一个与父类方法声明(方法名、参数列表)完全相同的方法。

  • 时机 :当从父类继承来的方法不能满足子类特定的需求时,就需要重写。

2. 格式与注解
  • 格式:子类方法的声明(方法名、参数列表)必须与父类方法一致。

  • @Override 注解:

    • 这是一个安全校验注解,加在子类重写的方法上。

    • 作用:由编译器检查该方法是否真的成功重写了父类方法。如果由于拼写错误等原因导致没有正确重写,编译器会报错。

    • 强烈建议重写时都加上此注解,保证代码安全、意图清晰。

3. 重写的核心规则 (重要!)
  1. 方法名与形参列表 :必须与父类被重写的方法完全相同。

  2. 访问权限 :子类方法的访问权限必须 >= 父类方法的访问权限。

    • public > protected > 默认(package-private) > private

    • 例如:父类是 protected,子类可以是 protected 或 public,但不能是默认或 private。

  3. 返回值类型:

    • 基本数据类型/void:必须完全相同。

    • 引用数据类型:子类方法的返回值类型可以是父类方法返回值类型的子类(即"小于等于")。

  4. 重写范围 :只有被声明为 非private、非final、非static 的实例方法(通常指进入了"虚方法表"的方法)才能被重写。

示例:

java

复制代码
class Animal {
    public void eat() {
        System.out.println("动物吃东西");
    }
    protected Animal getInstance() {
        return new Animal();
    }
}
class Cat extends Animal {
    @Override // 正确:重写了eat方法
    public void eat() {
        System.out.println("猫吃鱼");
    }
    @Override // 正确:返回值类型是Animal的子类
    public Cat getInstance() {
        return new Cat();
    }
}

六、继承中构造方法的访问特点

  1. 构造方法不能被继承:子类不能继承父类的构造方法。

  2. 隐式调用 :子类任何构造方法的第一行,都默认隐含了 super(),即先调用父类的无参构造。

    java

    复制代码
    public Student() {
        super(); // 默认存在,且必须在第一行
        // ... 子类构造后续代码
    }
  3. 显式调用 :如果父类没有无参构造,或者你想调用父类的有参构造,必须在子类构造方法的第一行使用 super(参数) 明确指定。

  4. this(...) 与 super(...) 在构造方法中不能共存,因为它们都要求位于第一行。

七、this 与 super 关键字总结

关键字 含义 调用位置
this 代表当前对象的引用(在内存中的地址)。 1. 访问本类成员变量:this.变量名 2. 访问本类成员方法:this.方法名() 3. 访问本类其他构造器:this(...) (必须第一行)
super 代表父类存储空间的标识(可以理解为父类对象的引用,但不等同于父类对象)。 1. 访问父类成员变量:super.变量名 2. 访问父类成员方法:super.方法名() 3. 访问父类构造器:super(...) (必须第一行)

核心区别 :this 指向当前实例本身,super 是子类中访问父类成员的桥梁,它不是一个独立的对象。

java 复制代码
package extensdemotext;

public class Employee {
    private  String id;
    private  String name;
    private  String position;

    public Employee() {
    }

    public Employee(String id, String name,String position) {
        this.id = id;
        this.name = name;
        this.position = position;
    }

    public String getId() {
        return id;
    }

    public void setId(String id) {
        this.id = id;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }
    public String getPosition(){
        return position;
    }
    public void setPosition(String position){
        this.position = position;
    }

    public void work(){
        System.out.println("员工在工作");
    }
}


package extensdemotext;

public class Teacher extends Employee{
    public Teacher() {
    }

    public Teacher(String id, String name,String position) {
        super(id, name, position);
    }

    @Override
    public void work(){
        System.out.println("教研部员工正在工作");
    }
}


package extensdemotext;

public class AdminStaff extends  Employee {
    public AdminStaff() {
    }

    public AdminStaff(String id, String name, String position) {
        super(id, name, position);
    }
    @Override
    public void work(){
        System.out.println("行政部员工在工作");
    }
}


package extensdemotext;

public class Lecturer extends Teacher{
    public Lecturer() {
    }

    public Lecturer(String id, String name,String position) {
        super(id, name, position);
    }
    @Override
    public void work(){
        System.out.println(getName()+"在上课");
    }
}


package extensdemotext;

public class Tutor extends Teacher{
    public Tutor() {
    }

    public Tutor(String id, String name,String position) {
        super(id, name,position);
    }
    @Override
    public void work(){
        System.out.println(getName()+"在批改作业");
    }
}

package extensdemotext;

public class Maintainer extends AdminStaff{
    public Maintainer() {
    }

    public Maintainer(String id, String name,String position) {
        super(id, name,position);
    }
    @Override
    public void work(){
        System.out.println(getName()+"在维护设施");
    }
}


package extensdemotext;

public class Buyer extends AdminStaff{

    public Buyer() {
    }

    public Buyer(String id, String name,String position) {
        super(id, name,position);
    }

    @Override
    public void work(){
        System.out.println(getName()+"在采购");
    }
}


package extensdemotext;

public class Test {
    public static void main(String[] args) {
        Lecturer l = new Lecturer("001","zhangsan","讲师");
        //System.out.println(l.getId()+", "+l.getName()+", "+l.getPosition());
        Tutor t = new Tutor("002","lisi","助教");
        Maintainer m = new Maintainer("003","wangwu","维护专员");
        Buyer b = new Buyer("004","zhaoniu","采购专员");
        l.work();
        t.work();
        m.work();
        b.work();




    }
}
相关推荐
掉进电商坑三年没爬出来的东叔13 分钟前
青龙面板进阶:一个面板聚合多平台签到,所有积分自动领
java·开发语言
ZhangJun9515 分钟前
Mobike 共享单车分析项目
人工智能·python·算法·kmeans·聚类·knn
XLYcmy17 分钟前
PDF 论文处理器 — 优势与功能文档
大数据·python·网络安全·pdf·dify·rag·漏洞检测
iCxhust25 分钟前
51单片机电力载波应用开发(七)广播通讯
c语言·开发语言·单片机·嵌入式硬件·51单片机
小猴子爱上树28 分钟前
跨马翻译:批量图片翻译+视频字幕+智能抠图,跨境电商在线图片翻译工具
大数据·人工智能·python·音视频
winfredzhang34 分钟前
用 Python 手写一个“所见即所得“的图片水印工具:wxPython + Pillow 实战详解
python·pillow·rotate·crop·身份改水印
殷色玫瑰1 小时前
C++ STL:stack、queue、priority_queue 与容器适配器详解
java·开发语言·数据结构·c++·算法·visualstudio
xUxIAOrUIII1 小时前
日常笔记-1005-1
linux·笔记·python·macos
yl45301 小时前
内蒙热门的废酸再生处理企业
大数据·python
IT方大同1 小时前
java输入输出+方法
java·开发语言·python