Java类和对象(五)—— 抽象类、接口、Object类和内部类

抽象类

在继承体系下,父类有些方法可能是要被重写的,如果我们事先就知道某些方法需要重写的话,我们可以不用在父类里面具体实现这个方法,这时候我们会用到抽象方法,这时候我们会用到关键字abstract关键字来修饰

public abstract class Animal {protected abstract void eat();
}

例如上面的Animal 类,每一个动物都会吃,但是每一个动物却吃的食物不同,父类的eat方法无法完全描述某个对象,这时候子类就需要重写这个方法,如果我们不想在父类具体实现这个eat方法的话,我们可以写成抽象方法~~

说完抽象方法,我们来类比一下抽象类:

如果一个类中没有包含足够的信息来描绘一个具体的对象,这样的类就是抽象类

抽象类也是用abstract 修饰的~~

注意要点

有抽象方法的类,一定是抽象类,所以如果方法被abstract修饰,那类也必须由abstract修饰,否则编译报错

抽象类是不能进行实例化的,但是可以有继承的向上转型和向下转型~~

被private、static、final 修饰的方法不能是抽象方法
因为抽象方法就是为了被子类重写的,根据重写的规则,被private、static、final修饰的方法确实不能被重写

抽象类被继承后,继承后子类要重写父类中的抽象方法除非子类也是抽象类,必须要使用 abstract 修饰,无论是谁继承了抽象类都必须重写所有的抽象方法,否则编译报错~~

在这里插入图片描述

在这里插入图片描述
当Dog继承Animal,必须重写Aniaml所有的抽象方法~~


在这里插入图片描述

在这里插入图片描述

如果Dog还是抽象类,Cat 继承 Dog,并且在 Cat 不是抽象的情况下,我们要在 Cat 这个类重写所有的抽象方法(即包括 Animal 也包括 Dog 的抽象方法)

抽象类的作用

抽象类就是用来被继承的
谁继承了抽象类,都必须重写抽象方法,否则编译报错,这也是为了多加一层编译器的校验

接口

接口就是公共的行为规范标准,大家在实现时,只要符合规范标准,就可以通用。
在Java中,接口可以看成是:多个类的公共规范,是一种引用数据类型

我们使用 intarface 来定义接口,就是把class替换成interface

,

public interface Ieat {void eat();
}

接口虽然不是类,但是接口编译完成后字节码文件的后缀格式也是.class
在这里插入图片描述

接口的使用规则

接口的成员方法是默认都是public static final 修饰的
接口的成员方法默认都是 public abstract 修饰的

当你在接口里定义了一个成员变量的时候,你必须对其进行初始化!!!
在这里插入图片描述

如果你想具体实现某些方法,你可以使用 static 或者 default 来进行修饰

public interface Ieat {static void eat(){//...}default void eat2(){//...}
}

访问权限也是和之前讲的是一样的,被static就是默认权限的静态方法,被default 修饰就是默认访问权限。


接口不能有实例化代码块、静态代码块,也不能有构造方法~~

在这里插入图片描述


如果类没有实现接口中的所有的抽象方法,则类必须设置为抽象类,如果被继承就必须重写所有的抽象方法!!!
这个和抽象类是类似的~~

在这里插入图片描述


软性规则:

创建接口时, 接口的命名一般以大写字母 I 开头.
接口的命名一般使用 “形容词” 词性的单词.
阿里编码规范中约定, 接口中的方法和属性不要加任何修饰符号, 保持代码的简洁性.

接口的继承

接口与接口之间可以多继承。即:用接口可以达到多继承的目的。
接口可以继承一个或者多个接口, 达到复用的效果. 使用 extends 关键字

interface IA{void eat();
}interface IB{void sleep();
}interface C extends IA,IB{}

接口的作用

解决了 Java 不能多继承的问题!!!
意味着一个类可以有多个接口!!!

如果子类由继承父类还有多个接口的时候,我们要先继承后接口(先extends 再 implements)

在这里插入图片描述

快捷键(搭建接口当中的抽象方法)

IDEA 中使用 ctrl + i 快速搭建接口当中的抽象方法~~

或者使用 alt + enter 进行选择implements methods 进行快速搭建接口,你选择Make ‘Dog’ abstract 的话就是讲这个类变为抽象类~~
在这里插入图片描述

接口的好处

public class Animal {protected String name;protected int age;
}public interface Irun {void run();
}public class Cat extends Animal implements Irun{public Cat(String name, int age) {this.name = name;this.age = age;}@Overridepublic void run() {System.out.println(this.name + "正在跑步");}
}public class Dog extends Animal implements Irun{public Dog(String name, int age) {this.name = name;this.age = age;}@Overridepublic void run() {System.out.println(this.name + "正在跑步");}
}public class Test {public static void walk(Irun irun){irun.run();}public static void main(String[] args) {walk(new Dog("旺财",11));walk(new Cat("小咪",10));}
}

在这里插入图片描述

接口也可以有动态绑定和多态~~
由于接口可以实现多态,所以程序员可以不关注类型,只要有这个接口的类,都能调用里面的接口方法,而不用去关心这是什么类。

Object 类

Object是Java默认提供的一个类。Java里面除了Object类,所有的类都是存在继承关系的。默认会继承Object父类。即所有类的对象都可以使用Object的引用。

在这里插入图片描述
我们这里先重点关注一下上面标出来的三个方法:toString,equals,hashCode,

toString(打印对象)

class Person{public String name;public int age;}public class Test {public static void main(String[] args) {Person person = new Person();System.out.println(person);}
}

我们在数组里知道直接打印数组名的话会出现包含数组的地址的一串字符串~~
如果直接打印对象的话,也会出现和数组类似的情况,这是为什么?

Java所有的类都会继承Object类,在调用println的时候,我们来看看一共调用了哪些方法:

首先println 方法如下:

在这里插入图片描述

之后无论是走if 语句还是else 语句,都会调用toString方法

在这里插入图片描述
在这里插入图片描述
最后就会来到toString 方法,这里getClass.getName()就是类名,然后加@符号,最后调用hashCode找到地址。


但是如果我们重写了 toString 方法的话,根据前面的知识,优先调用子类的方法来打印对象内容。

class Person{public String name;public int age;@Overridepublic String toString() {return "Person{" +"name='" + name + '\'' +", age=" + age +'}';}
}

这样的话,我们就会优先调用子类自己的toString 方法

在这里插入图片描述


我们可以使用编译器自动生成toString方法:

在这里插入图片描述

在这里插入图片描述

和之前搭建getter、setter还有构造方法是一样的,只是这里选择的是toString()

class A{public String name;public int age;@Overridepublic String toString() {return "A{" +"name='" + name + '\'' +", age=" + age +'}';}
}

equals

在Java当中,如果使用 == 来进行比较时
如果比较的是基本数据类型的话,就是比较两个的数值相不相同
如果比较的是引用数据类型,就会比较他们的地址相不相同

来我们看一下源码:

在这里插入图片描述

还是一样的,直接调用equals方法,还是比较两个对象的地址,所以如果想比较两个对象的内容相不相同就必须重写equals方法~~

    public boolean equals(Object o) {if (this == o) return true;if (o == null || getClass() != o.getClass()) return false;Person person = (Person) o;return age == person.age && Objects.equals(name, person.name);}
class Person{public String name;public int age;public Person(String name, int age) {this.name = name;this.age = age;}@Overridepublic String toString() {return "Person{" +"name='" + name + '\'' +", age=" + age +'}';}@Overridepublic boolean equals(Object o) {if (this == o) return true;if (o == null || getClass() != o.getClass()) return false;Person person = (Person) o;return age == person.age && Objects.equals(name, person.name);}
}public class Test {public static void main(String[] args) {Person person1 = new Person("张三",10);Person person2 = new Person("张三",10);System.out.println(person1.equals(person2));}
}

在这里插入图片描述

比较对象中内容是否相同的时候,一定要重写equals方法。

hashCode

源码:

在这里插入图片描述

native 说明这是本地方法,这个是有C/C++代码编写的,我们是看不到的


简单来说,hashCode方法可以找到对象的内存地址

public class Test {public static void main(String[] args) {Person person1 = new Person("张三",10);Person person2 = new Person("张三",10);System.out.println(person1.hashCode());System.out.println(person2.hashCode());}
}

在这里插入图片描述

由于这是两个不同的对象,所以他们的内存地址是不一样的~~

但是如果我们认为当两个对象的内容是一样的,那地址就应该是一样的话,我们就需要重写hashCode 方法~~

    @Overridepublic int hashCode() {return Objects.hash(name, age);}

在这里插入图片描述

这样他们的地址就会是一样的显示~~


快捷键搭建

以上三个方法都能使用快捷键快速搭建:

在这里插入图片描述

内部类

内部类就是在类里面再定义一个类,这个类定义的位置和外部类的成员是相同的。

静态内部类

static修饰的内部成员类称为静态内部类。

class A{public int age;public static int price;public A(){System.out.println("A()......");}public void methodA1(){System.out.println("methodA1()......");}public static void methodA2(){System.out.println("methodA2()......");}static class B{public void methodB(){//age = 10;//err,静态内部类只能访问外部类的静态成员//A();//不要在静态内部类中调用外部类的构造方法,构造方法是没有静态的,所以构造方法一定不是静态方法//methodA1(); //err,静态内部类只能访问外部类的静态成员,methodA1不是类方法(静态成员方法)price = 10;methodA2();}}//.....
}

注意事项

静态内部类只能访问外部类的静态成员

创建静态内部类

A.B b = new A.B();

我们可以将静态内部类当成外部类的一个静态成员,静态成员的访问不需要创建对象,我们可以通过类名来访问,于是我们通过 A.B 就访问到了静态内部类,然后就通过new A.B 就可以完成创建了

实例内部类

未被static 修饰的实例内部类就是实例内部类

实例内部类可以自由访问外部类的任意成员,如果实例内部类和外部类有重名的成员时,在内部类中优先访问自己的,如果真的相访问外部类同名的成员时,我们可以使用 外部类类名.this.成员 即可~~

class A{public int age;public static int price;public A(){System.out.println("A()......");}public void methodA1(){System.out.println("methodA1()......");}public static void methodA2(){System.out.println("methodA2()......");}public void methodA3(){System.out.println("methodA3()......");}class C{public int age = 10;public void methodC(){System.out.println(age);methodA3();System.out.println(A.this.age);methodA1();A.this.methodA1();}public void methodA1(){System.out.println("C::methodA1()......");}}//.....
}public class Test{public static void main(String[] args) {A.C c = new A().new C();c.methodC();}
}

在这里插入图片描述


创建实例内部类

我们要先创建外部类,再去创建实例内部类

A.C c = new A().new C();

当然也可以分部去写:

A a = new A();
A.C c = a.new C();

注意事项

1.外部类中的任何成员都 可以在实例内部类方法中直接访问
2.实例内部类所处的位置与外部类成员位置相同,因此也受public、private等访问限定符的约束
3.在实例内部类方法中访问同名的成员时,优先访问自己的,如果要访问外部类同名的成员,必须:外部类名
称.this.同名成员 来访问
4.实例内部类对象必须在先有外部类对象前提下才能创建
5.实例内部类的非静态方法中包含了一个指向外部类对象的引用
6.外部类中,不能直接访问实例内部类中的成员,如果要访问必须先要创建内部类的对象。


匿名内部类

class A{public void test1(){System.out.println("heihei");}
}public class Test{public static void main(String[] args) {new A(){}.test1();}}

在这里插入图片描述

通过后面的 .方法 来调用相应的方法。


我们也可以重写匿名内部类的方法

在这里插入图片描述
在这里插入图片描述


在这里插入图片描述
但是要注意不能使用对象来接收匿名内部类


接口也可以使用:

interface A{void test1();
}public class Test{public static void main(String[] args) {new A(){public void test1(){System.out.println("haha");}};}}

和上面不一样的是,接口是一定要重写其中的抽象方法的,并且花括号后面是不能直接 .方法 的,而是要通过被接收后,然后去再去调用相应的方法~~

因此接口是可以被接收的,接收后也是可以继续使用的:

在这里插入图片描述
在这里插入图片描述

局部内部类

局部内部类是定义在方法里的,因此它的生命周期和方法是一样。

    public void A() {//...class D{ //......}//...}

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

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

【人工智能】模型性能评估

模型性能衡量介绍 混淆矩阵 混淆矩阵(Confusion Matrix) TP(真阳性):预测为阳性,且预测正确。 TN(真阴性):预测为阴性,且预测正确。 FP(伪阳性):预测为阳性,但预测错误,又称型一误…

Vue3骨架屏(Skeleton)

效果如下图:在线预览 APIs 参数说明类型默认值必传animated是否展示动画效果booleantruefalsebutton是否使用按钮占位图boolean | SkeletonButtonPropsfalsefalseavatar是否显示头像占位图boolean | SkeletonAvatarPropsfalsefalseinput是否使用输入框占位图boolea…

2024.05.24 学习记录

1、面经复习: js基础、知识深度、js垃圾回收 2、代码随想录刷题:动态规划 完全背包 all 3、rosebush 完成 Tabs、Icon、Transition组件

ENVI光谱识别指导采矿管理者监测铜矿分布

圣地亚哥SRGIS的GIS专家Chile需要利用影像光谱信号勘察Chuquicamata的铜矿分布。 解决方案 Chuquicamata是世界上最大的斑岩铜矿分布区。SRGIS发现西部地区只有有限的矿物和贫瘠的岩石,但东部有铜矿分布。为了进一步测定矿藏的情况,他们开发出一套程序&a…

【算法】双指针

1、移动零 1.1 题目解析 可以发现&#xff0c;这道题的本质就是通过某一个标准&#xff0c;将数组划分成不同区间(数组划分、数组分块)&#xff0c;此时可以用到双指针算法 1.2 算法原理讲解 1.3 代码实现 class Solution { public:void moveZeroes(vector<int>& …

强化学习算法

从上图看出&#xff0c;强化学习可以分成价值/策略、随机策略/确定策略、在线策略/离线策略、蒙特卡洛/时间差分这四个维度。这里分析了基础算法中除了在线策略/离线策略以外的其他维度。 &#xff08;一&#xff09;基础知识 一、基础概念 重点概念&#xff1a;状态S、动作A、…

【全网最全】2024电工杯数学建模A题21页初步参考论文+py代码+保奖思路等(后续会更新)

您的点赞收藏是我继续更新的最大动力&#xff01; 一定要点击如下的卡片链接&#xff0c;那是获取资料的入口&#xff01; 【全网最全】2024电工杯数学建模A题21页初步参考论文py代码保奖思路等&#xff08;后续会更新成品论文&#xff09;「首先来看看目前已有的资料&#x…

每周刷题第三期

个人主页&#xff1a;星纭-CSDN博客 系列文章专栏&#xff1a;Python 踏上取经路&#xff0c;比抵达灵山更重要&#xff01;一起努力一起进步&#xff01; 目录 题目一&#xff1a;环形链表 题目二&#xff1a;删除有序数组中的重复项 题目三&#xff1a;有效的括号 题…

HCIP【VRRP、MSTP、VLAN综合实验】

目录 一、实验拓扑图&#xff1a; ​编辑二、实验要求 三、实验思路 四、实验步骤 &#xff08;1&#xff09; eth-trunk技术配置 &#xff08;2&#xff09;vlan 技术配置 &#xff08;3&#xff09;配置SW1、SW2、AR1、ISP的IP地址 &#xff08;4&#xff09;在交换机…

Java+Spring+ MySQL + MyCat云HIS有哪些优势?智慧医疗云(HIS)低成本与安全保障的完美结合

JavaSpring MySQL MyCat云HIS有哪些优势&#xff1f;智慧医疗云(HIS)低成本与安全保障的完美结合 云HIS的优点包括节省成本、便捷高效、稳妥安全等。通过云HIS&#xff0c;医疗机构无需在本地建立机房、购买服务器和应用软件&#xff0c;降低了硬件和人力成本。同时&#xff0…

图片、视频画质增强变清晰工具分享(免费)

生活中可能会修一下模糊图片那么这就有一款用来修图片的管理工具&#xff0c;也有可能会修一下模糊的视频&#xff0c;在吾爱上有大佬开发了这么一款工具&#xff0c;免费的&#xff0c;不需要开任何VIP&#xff0c;我试了一下&#xff0c;好用&#xff0c;分享出来&#xff0c…

antd-vue a-tree 当两个不同一级下二级key相同的时候就会导致两个同时选择, 拿到node.parent的数据也会出问题, 解决办法

一、问题如下图&#xff1a; 当两个不同一级下二级key相同的时候就会导致两个同时选择&#xff0c; 同时拿到node.parent的数据也会出问题, 出现一下问题的原因是因为数据treeData 的key出现相同的了 然后如下图、因为我的查询条件 第二层是给 cloud , 第二层是给 relatedPool…

树洞陪聊系统源码/陪聊/陪玩/树洞/陪陪/公众号开发/源码交付/树洞系统源码

独立版本源码交付&#xff0c;自研UI和前后端代码 平台自带店员&#xff0c;无需自主招募&#xff0c;搭建直接运营 支持三方登录&#xff0c;官方支付、虎皮椒、易支付/码支付 支持首单体验、盲盒订单、指定下单等多个模式 支持钱包预充值、店员收藏、订单评价等功能 支持…

什么样的数据摆渡设备,可以满足不同网间数据的安全传输需求?

数据摆渡设备是用来在不同的网络环境间安全地传输数据的硬件或软件解决方案。它们通常用于确保在具有不同安全级别的网络&#xff08;如内网和外网&#xff09;之间进行数据交换时的安全性和合规性。以下是一些常见的数据摆渡设备和方法&#xff1a; 移动介质拷贝&#xff1a;使…

Python模块、包和异常处理

大家好&#xff0c;在当今软件开发领域&#xff0c;Python作为一种简洁、易读且功能强大的编程语言&#xff0c;被广泛应用于各种领域。作为一名测试开发工程师&#xff0c;熟练掌握Python的模块、包和异常处理是提高代码可维护性和错误处理能力的关键。本文将和大家一起探讨Py…

第七节 ConfigurationClassParser 源码分析

tips&#xff1a; ConfigurationClassParser 是 Springframework 中的重要类。 本章主要是源码理解&#xff0c;有难度和深度&#xff0c;也枯燥乏味&#xff0c;可以根据实际情况选择阅读。 位置&#xff1a;org.springframework.context.annotation.ConfigurationClassPars…

Java方法的重载

Java方法的重载 前言一、为什么要有重载代码示例问题 代码示例 二、重载的使用代码示例 三、重载的规则针对同一个类代码示例 前言 推荐一个网站给想要了解或者学习人工智能知识的读者&#xff0c;这个网站里内容讲解通俗易懂且风趣幽默&#xff0c;对我帮助很大。我想与大家分…

HTML5好看的通用网站模板源码

文章目录 1.设计来源1.1 主界面1.2 模板菜单1 界面1.3 模板菜单2 界面1.4 模板菜单3 界面1.5 下拉菜单1 界面1.6 下拉菜单2 界面1.7 模板菜单4 界面1.8 模板菜单5 界面1.9 界面底部 2.效果和源码2.1 动态效果2.2 源码目录2.3 源代码 源码下载 作者&#xff1a;xcLeigh 文章地址…

django-celery-beat自动调度异步任务

Celery是一个简单、灵活且可靠的分布式系统&#xff0c;专门用于处理大量消息的实时任务调度。它支持使用任务队列的方式在分布的机器、进程、线程上执行任务调度。Celery不仅支持异步任务&#xff08;如发送邮件、文件上传、图像处理等耗时操作&#xff09;&#xff0c;还支持…

深度学习之基于Tensorflow卷积神经网络(CNN)实现猫狗识别

欢迎大家点赞、收藏、关注、评论啦 &#xff0c;由于篇幅有限&#xff0c;只展示了部分核心代码。 文章目录 一项目简介 二、功能三、系统四. 总结 一项目简介 一、项目背景与意义 在人工智能和深度学习的热潮中&#xff0c;图像识别是一个备受关注的领域。猫狗识别作为图像识…