Java 三大特性之继承

news2025/1/11 20:58:36

目录

一、为什么需要继承?

二、继承概念

三、继承的语法

四、子类访问父类成员

五、super关键字

六、继承关系下的构造方法

七、继承关系下的初始化

八、protected关键字

 九、继承的三种方式

十、final关键字 

十一、继承和组合


一、为什么需要继承?

比如狗和猫,他们都是一个动物,吃饭睡觉是他们的共性,如果你单独写狗类和猫类,会有大量的代码重复

//Cat.java
public class Cat{
    public String name;
    public void eat(){
        System.out.println(name + "正在吃饭"); 
    }
    public void sleep(){
        System.out.println(name + "正在睡觉");
    }
    void say(){
        System.out.println(name + "喵喵~");
    }
}

//Dog.java
public class Dog{
    public String name;
    public void eat(){
        System.out.println(name + "正在吃饭");
    }
    public void sleep(){
        System.out.println(name + "正在睡觉");
    }
    void say(){
        System.out.println(name + "汪汪~");
    }
}

那能否将这些共性抽取呢?

面向对象思想中提出了继承的概念,专门用来进行共性抽取,实现代码复用


二、继承概念

继承(inheritance)机制:是面向对象程序设计使代码可以复用的最重要的手段,它允许程序员在保持原有类特性的基础上进行扩展,增加新功能,这样产生新的类,称派生类。继承呈现了面向对象程序设计的层次结构, 体现了由简单到复杂的认知过程。继承主要解决的问题是:共性的抽取,实现代码复用

上述图示中,Cat和Dog都继承了Animal类,其中:Animal类称为 父类/基类或超类,Cat和Dog可以称为Animal的 子类/派生类,继承之后,子类可以复用父类中成员,子类在实现时只需关心自己新增加的成员即可。 


三、继承的语法

修饰词 class 子类 extends 父类 {
    //...
}   

重写上面那个例子 

//Animal.java
public class Animal {
    public String name;
    public void eat(){
        System.out.println(name + "正在吃饭");
    }
    public void sleep() {
        System.out.println(name + "正在睡觉");
    }
}

//Cat.java
public class Cat extends Animal{
    void say(){
        System.out.println(name + "喵喵~");
    }
}

//Dog.java
public class Dog extends Animal{
    void say(){
        System.out.println(name + "汪汪~");
    }
}

//Test.java 
public class Test {
    public static void main(String[] args) {
        Dog dog = new Dog();
        dog.name = "小狗";
        //Dog类从Animal类继承下的成员变量
        System.out.println(dog.name);
        //Dog类从Animal类继承下的方法
        dog.eat();
        dog.sleep();
        //这是个性的方法
        dog.say();
    }
}

【注意】

  1. 子类会将父类中的成员变量或者成员方法继承到子类中了
  2. 子类继承父类之后,必须要新添加自己特有的成员,体现出与基类的不同,否则就没有必要继承了

四、子类访问父类成员

子类中访问父类的成员变量或者成员方法

(1)子类和父类 不存在 同名成员

先访问子类再访问父类,没有就报错!

(2)子类和父类 存在 同名成员

访问子类自己;

【注意】

  • 成员方法重名,但是参数列表不同(方法重载),根据调用方法时传递的参数选择合适的方法访问,如果没有则报错;

可以看到,如果子类和父类存在同名,怎么才能在子类中访问父类相同名称的成员呢?


五、super关键字

该关键字主要作用:在子类方法中访问父类的成员。

【注意】

  1. 只能在非静态方法中使用
  2. 在子类方法中,访问父类的成员变量和方法。
//A.java
public class A{
    int a ;
    void methodA(){
        //...
    }
    void methodB(int a){
        //...
    }
}

//B.java
public class B extends A{
    int a ;
    //与父类中methodA()构成重写
    void methodA(){
        //...
    }

    //与父类中methodB()构成重载(参数列表不同)
    void methodB(){
        //...
    }
    
    void methodC(){ //在子类方法中访问父类成员
        //通过super关键字访问父类成员
        super.a = 111;
        super.methodA();

        //直接可以通过参数列表区分清访问父类还是子类方法
        methodB();    //子类
        methodB(20);    //父类

    }
}

六、继承关系下的构造方法

子类对象构造时,需要先调用父类构造方法,然后执行子类的构造方法

//A.java
public class A{
    public A(){
        System.out.println("父类构造方法");
    }
}

//B.java
public class B extends A{
    public B(){
        System.out.println("子类构造方法");
    }
}

//Test.java
public class Test{
    public static void main(String[] args) {
        B b = new B();    //实例化对象,调用构造方法
    }
}

//输出
//父类构造方法
//子类构造方法

 【注意】

  1. 若父类显式定义无参或者默认的构造方法,在子类构造方法第一行默认有隐含的super()调用,即调用基类构造方法
  2. 如果父类构造方法是带有参数的,此时需要用户为子类显式定义构造方法,并在子类构造方法中选择合适的 父类构造方法调用,否则编译失败。
  3. 在子类构造方法中,super(...)调用父类构造时,必须是子类构造函数中第一条语句。
  4. super(...)只能在子类构造方法中出现一次,并且不能和this同时出现

七、继承关系下的初始化

没继承关系下的执行顺序:静态代码块 > 实例代码块 > 构造方法 

有继承关系下的执行顺序:

//A.java
public class A{
    public A(){
        System.out.println("父类构造方法");
    }
    {
        System.out.println("父类实例代码块");
    }
    static{
        System.out.println("父类静态代码块");
    }

}

//B.java
public class B extends A{
    public B(){
        System.out.println("子类构造方法");
    }
    {
        System.out.println("子类实例代码块");
    }
    static{
        System.out.println("子类静态代码块");
    }
}

//Test.java
public class Test{
    public static void main(String[] args) {
        B b1 = new B();    //实例化第一个对象
        System.out.println("===========");
        B b2 = new B();    //实例化第二个对象
    }
}

【结论】

  1. 父类静态代码块优先于子类静态代码块执行,且是最早执行
  2. 父类实例代码块和父类构造方法紧接着执行
  3. 子类的实例代码块和子类构造方法紧接着再执行
  4. 第二次实例化子类对象时,父类和子类的静态代码块都将不会再执行

八、protected关键字

//A.java
package demo1;
public class A {
    public int x;
    protected int y;
}

//C.java
package demo2;
import demo1.A;
public class C extends A{
    public static void main(String[] args) {
        C c = new C();
        c.x = 20;
        c.y = 10;
    }
}

//B.java
package demo2;
public class B {
    public static void main(String[] args) {
        //因为B和A不是父子关系,得通过C这个A的子类来访问父类成员,建立关系
        //B的意义就是代表 不同包中的类
        C c = new C();    
        System.out.println(c.x);
        //protected 不能在不同包中的非子类直接访问
        //c.y = 100;
    }
}

 九、继承的三种方式


十、final关键字 

final关键可以用来修饰变量、成员方法以及类。

(1)修饰变量或字段,表示常量(即不能修改)

(2)修饰类:表示此类不能被继承

//A.java
public final class A{    //final 修饰
    //...
}

//B.java
public class B extends A{  //报错
   //...
}

 (3)修饰方法:表示该方法不能被重写(后序介绍)


十一、继承和组合

组合可以实现类似多继承的效果,但是和多继承是不一样的喔!

继承表示对象之间是 is-a 的关系,比如:狗是动物,猫是动物

组合表示对象之间是 has-a 的关系,比如:汽车

汽车和其轮胎、发动机、方向盘、车载系统等的关系就应该是组合,因为汽车是有这些部件组成的。

class Tire{ //轮胎
    //...
}
class Engine{   //发动机
    //...
}
//方向盘类...
class Car{  //将上面的类组合到一起
    private Tire tire;  //可以复用轮胎的成员
    private Engine engine;  //可以复用发动机的成员
    //...
}

//比亚迪是汽车
class BYD extends Car{
    //将汽车中包含的:轮胎、发送机等都继承下来
}

组合和继承都可以实现代码复用,应该使用继承还是组合,需要根据应用场景来选择,一般建议:能用组合尽量用组合。


本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1654587.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

可视化面板布局适配屏幕-基于 flexible.js + rem 智能大屏适配

可视化面板布局适配屏幕-基于 flexible.js rem 智能大屏适配 VScode 安装cssrem插件引入flexible.js在之后的开发都使用rem为单位,安装cssrem插件就是为了快捷将px转为rem我们的设计稿是1920px,设置最小宽度为1024px,最后,我们可…

(2024,LSTM,Transformer,指数门控,归一化器状态,多头内存混合)xLSTM:扩展的 LSTM

xLSTM: Extended Long Short-Term Memory 公和众和号:EDPJ(进 Q 交流群:922230617 或加 VX:CV_EDPJ 进 V 交流群) 目录 0. 摘要 1. 简介 2. 扩展的 LSTM 2.1 LSTM 回顾 2.2 sLSTM 2.3 mLSTM 2.4 xLSTM 架构 2…

Java进阶06List集合泛型

Java进阶06 集合 一、集合及其体系结构 集合是一个长度可变的容器 1、集合的体系结构 1.1 单列集合 单列集合使用add()方法添加集合元素,一次只能添加一个元素。 单列集合均实现了Collection接口,该接口还有两个子接口List和Set。 List接口 List集合…

详细分析McCabe环路复杂度(附例题)

目录 前言1. 基本知识2. 例题 前言 该知识点常出在408或者软考中,对此此文重点讲讲理论知识以及例题 对于例题平时看到也会更新 1. 基本知识 McCabe环路复杂度是一种用于衡量软件代码复杂性的指标,主要是通过计算代码中的控制流图中的环路数量来衡量…

为什么选择ATECLOUD自动化测试平台?

在当今飞速发展的时代,一切都在不断进步与变革,电测行业也由手动测试逐步转向了自动化测试。但是随着科技的发展,对于产品的测试要求也越来越高,传统的自动化测试系统已经无法满足用户日益增长的测试需求,全新的ATE测试…

全国33个省228189个矿产地位置分布数据,含经纬度坐标/CSV格式

全国矿产地分布(2021版) 数据来源: 全国矿产地数据库2021版 (ngac.org.cn) http://data.ngac.org.cn/mineralresource/index.html 数据获取方法:树谷资料库大全(2024年4月19日更新) 进入网站后&#xf…

【Qt 开发基础体系】Qt信号与槽机制

文章目录 1.Qt 信号与槽机制原理(Signal & Slot)2. QObject 类 connect 的介绍3. 信号与槽机制连接方式4. 信号和槽机制优势及其效率:3. 信号与槽机制应用 1.Qt 信号与槽机制原理(Signal & Slot) &#x1f42…

cesium雷达扫描(消逝圆效果)

cesium雷达扫描(消逝圆效果) 以下为源码直接复制可用 1、实现思路 通过修改“material”材质来实现轨迹球效果 2、示例代码 1、index.html <!DOCTYPE html> <html lang="en"><head><!

程序的机器级表示——Intel x86 汇编讲解

往期地址&#xff1a; 操作系统系列一 —— 操作系统概述操作系统系列二 —— 进程操作系统系列三 —— 编译与链接关系操作系统系列四 —— 栈与函数调用关系操作系统系列五 —— 目标文件详解操作系统系列六 —— 详细解释【静态链接】操作系统系列七 —— 装载操作系统系列…

漏扫神器Invicti V2024.4.0专业版

前言 Invicti Professional是Invicti Security公司推出的一个产品&#xff0c;它是一种高级的网络安全扫描工具。Invicti Professional旨在帮助组织发现和修复其网络系统中的潜在安全漏洞和弱点。它提供了全面的漏洞扫描功能&#xff0c;包括Web应用程序和网络基础设施的漏洞扫…

水库安全无忧,漫途智能监测方案守护大坝安全!

水库大坝作为水利工程的重要组成部分&#xff0c;不仅承担着防洪、蓄水、灌溉、发电等多重功能&#xff0c;同时也关系着人民群众的生命财产安全。 然而&#xff0c;随着时间的推移&#xff0c;许多水库大坝存在稳定性不足、渗漏现象严重、裂缝和断面不足等问题&#xff0c;安…

[C++]哈希应用-布隆过滤器快速入门

布隆过滤器 布隆过滤器&#xff08;Bloom Filter&#xff09;是一个由布隆在1970年提出的概率型数据结构&#xff0c;它实际上是一个很长的二进制向量和一系列随机映射函数。布隆过滤器的主要特点是高效的插入和查询&#xff0c;可以用于检索一个元素是否在一个集合中。 原理…

射频无源器件之耦合器

一. 耦合器的作用 在射频电路中,射频耦合器将一路微波功率按比例分成几路,用于检测或监测信号,如功率测量和波检测,还可改变信号的幅度、相位等特性,以满足不同的通信需求。根据输入与耦合端的功率差,常被分为5dB、6dB、10dB等耦合器。射频耦合器的类型主要包括定向耦合…

Infuse for Mac激活版:高清影音播放软件

对于热爱影音娱乐的Mac用户来说&#xff0c;Infuse for Mac是一个不容错过的选择。它以其简洁的操作界面和强大的播放功能&#xff0c;为用户带来了全新的影音播放体验。 Infuse for Mac支持广泛的音视频格式&#xff0c;无需额外转换&#xff0c;即可轻松播放您喜爱的影片。无…

2024年教育创新与人文艺术国际学术会议(ICEIHA 2024)

2024年教育创新与人文艺术国际学术会议(ICEIHA 2024) 2024 International Conference on Educational Innovation and Humanities and Arts 一、【会议简介】 2024年教育创新与人文艺术国际学术会议&#xff0c;将探讨教育创新与人文艺术的结合。 本次会议将汇集全球的专家学者…

使用idea管理docker

写在前面 其实idea也提供了docker的管理功能&#xff0c;比如查看容器列表&#xff0c;启动容器&#xff0c;停止容器等&#xff0c;本文来看下如何管理本地的docker daemon和远程的dockers daemon。 1&#xff1a;管理本地 双击shift&#xff0c;录入service&#xff1a; …

【3dmax笔记】026:挤出和壳修改器的使用

文章目录 一、修改器二、挤出三、壳 一、修改器 3ds Max中的修改器是一种强大的工具&#xff0c;用于创建和修改复杂的几何形状。这些修改器可以改变对象的形状、大小、方向和位置&#xff0c;以生成所需的效果。以下是一些常见的3ds Max修改器及其功能&#xff1a; 挤出修改…

C++学习————第十天(string的基本使用)

1、string 对象类的常见构造 (constructor)函数名称 功能说明&#xff1a; string() &#xff08;重点&#xff09; 构造空的string类对象&#xff0c;即空字符串 string(const char* s) &#xff08;重点&#xff09;…

二层交换机与防火墙连通上网实验

防火墙是一种网络安全设备&#xff0c;用于监控和控制网络流量。它可以帮助防止未经授权的访问&#xff0c;保护网络免受攻击和恶意软件感染。防火墙可以根据预定义的规则过滤流量&#xff0c;例如允许或阻止特定IP地址或端口的流量。它也可以检测和阻止恶意软件、病毒和其他威…

【linux软件基础知识】-死锁问题

死锁问题 当两个或多个线程由于每个线程都在等待另一个线程持有的资源而无法继续时,就会发生死锁 如下图所示, 在线程 1 中,代码持有了 L1 上的锁,然后尝试获取 L2 上的锁。 在线程 2 中,代码持有了 L2 上的锁,然后尝试获取 L1 上的锁。 在这种情况下,线程 1 已获取 L…