新手小白学JAVA 面向对象之多态

article/2025/9/12 23:00:04

多态

1. 概念

多态是面向对象程序设计(OOP)的一个重要特征,指同一个实体同时具有多种形式,即同一个对象,在不同时刻,代表的对象不一样,指的是对象的多种形态。

可以把不同的子类对象都当作父类来看,进而屏蔽不同子类对象之间的差异,写出通用的代码,做出通用的编程,统一调用标准。

比如,你的女盆友让你买点水果回来,不管买回来的是苹果还是西瓜,只要是水果就行,这个就是生活中多态的体现

再比如,小猫、小狗、小猪我们可以把他们都归纳成小动物,每种小动物都需要吃东西,所以我们可以统一设置他们都必须吃,但是每种小动物的习性不一样,那这个就可以设置成小动物自己特有的功能,多态对象只能调用父类中定义子类中重写的功能,并不能调用子类的特有功能,这样就实现了代码的统一

2 . 特点

  1. 多态的前提1:是继承
  2. 多态的前提2:要有方法的重写
  3. 父类引用指向子类对象,如:Animal a = new Cat();
  4. 多态中,编译看左边,运行看右边
    在这里插入图片描述

3. 练习:多态入门案例

创建包: cn.tedu.oop
创建类: TestDemo.java

package cn.tedu.oop2;
/*本类用作多态的入门案例*/
public class TestDemo {public static void main(String[] args) {//6.创建“纯纯的”对象用于测试Animal a = new Animal();Cat c = new Cat();Dog d = new Dog();a.eat();//小动物Animal吃啥都行~调用的是父类自己的功能c.eat();//小猫爱吃小鱼干~调用的是子类重写后的功能d.eat();//小狗爱吃肉骨头~调用的是子类重写后的功能/*2.父类对象不可以使用子类的特有功能*///a.jump();//报错,Animal类里并没有这个方法//a.run();//报错,Animal类里并没有这个方法c.jump();//小猫Cat跳的老高啦~,子类可以调用自己的功能d.run();//小狗Dog跑的老快啦~,子类可以调用自己的功能//7.创建多态对象进行测试/*3.口诀1:父类引用指向子类对象* 解释:创建出来的子类对象的地址值,交给父类类型的引用类型变量来保存*/Animal a2 = new Cat();//Cat类对象的地址值交给父类型变量a2来保存Animal a3 = new Dog();//Dog类对象的地址值交给父类型变量a3来保存//8.测试多态对象/*4.口诀2:编译看左边,运行看右边* 解释:必须要在父类定义这个方法,才能通过编译,把多态对象看作是父类类型*      必须要在子类重写这个方法,才能满足多态,实际干活的是子类*/a2.eat();//小猫爱吃小鱼干~,多态对象使用的是父类的定义,子类的方法体}
}
/*1.多态的前提:继承+重写*/
//1.创建父类
class Animal{//3.创建父类的普通方法public void eat(){System.out.println("小动物Animal吃啥都行~");}
}
//2.1创建子类1
class Cat extends Animal{//4.1添加重写的方法public void eat(){System.out.println("小猫爱吃小鱼干~");}//5.1添加子类的特有功能public void jump(){System.out.println("小猫Cat跳的老高啦~");}
}
//2.2创建子类2
class Dog extends Animal{//4.2添加重写的方法@Overridepublic void eat(){System.out.println("小狗爱吃肉骨头~");}//5.2添加子类的特有功能public void run(){System.out.println("小狗Dog跑的老快啦~");}
}

4. 多态的好处

  1. 多态可以让我们不用关心某个对象到底具体是什么类型,就可以使用该对象的某些方法
  2. 提高了程序的可扩展性和可维护性

5. 多态的使用

前提:多态对象把自己看做是父类类型

  1. 成员变量: 使用的是父类的
  2. 成员方法: 由于存在重写现象,所以使用的是子类的
  3. 静态成员: 随着类的加载而加载,谁调用就返回谁的

6. 练习:多态成员使用测试

创建包: cn.tedu.oop
创建类: TestDemo2.java

package cn.tedu.oop2;
/*本类用于测试多态成员的使用情况*/
public class TestDemo2 {public static void main(String[] args) {//7.创建纯纯的子类对象Dog2 d = new Dog2();System.out.println(d.sum);//20,子类自己的属性d.eat();//小狗爱吃肉包子,子类自己的方法//8.创建多态对象/*口诀1:父类引用指向子类对象*//*口诀2:编译(保存)看左边,运行(效果)看右边*/Animal2 a = new Dog2();/*多态中,成员变量使用的是父类的*/System.out.println(a.sum);//10/*多态中,方法的声明使用的是父类的,方法体使用的是子类的*/a.eat();//小狗爱吃肉包子/*多态中,调用的静态方法是父类的,因为多态对象把自己看作是父类类型* 直接使用父类中的静态资源*/a.play();//没有提示,玩啥都行~Animal2.play();}
}
//1.创建父类
class Animal2{//3.创建父类的成员变量int sum = 10;//4.创建父类的普通方法public void eat(){System.out.println("吃啥都行~");}//9.1定义父类的静态方法playpublic static void play(){System.out.println("玩啥都行~");}
}
//2.创建子类
class Dog2 extends Animal2{//5.定义子类的成员变量int sum = 20;//6.重写父类的方法@Overridepublic void eat(){System.out.println("小狗爱吃肉包子");}//9.2创建子类的静态方法play//@Override/*这不是一个重写的方法,只是恰巧在两个类中出现了一模一样的两个静态方法* 静态方法属于类资源,只有一份,不存在重写的现象* 在哪个类里定义,就作为哪个类的资源使用*/public static void play(){System.out.println("小狗喜欢玩皮球~");}
}

7 拓展

7.1 设计汽车综合案例

创建包: cn.tedu.oopexec
创建类: DesignCar.java

package cn.tedu.oop2;
/*本类用于完成汽车设计案例*/
public class DesignCar {public static void main(String[] args) {//9.创建一个纯纯的父类对象进行测试Car c = new Car();System.out.println(c.getColor());//nullc.start();c.stop();//c.swim();//报错,父类对象不可以调用子类的特有功能//10.创建纯纯的子类对象做测试BMW b = new BMW();System.out.println(b.color);//五彩斑斓的黑System.out.println(b.getColor());//nullb.start();//都让开,我的车要起飞啦~b.stop();//唉呀妈呀熄火了~//11.创建多态对象进行测试Car c2 = new TSL();//System.out.println(c2.color);System.out.println(c2.getColor());c2.stop();c2.start();//c2.swim();}
}
//1.通过分析,抽象形成一个汽车类
class Car{//2.定义并封装汽车类的属性--成员变量private String brand;//品牌private String color;//颜色private int id;//编号private double price;//价格//3.定义功能public void start(){System.out.println("我的小车车启动啦~");}public void stop(){System.out.println("唉呀妈呀熄火了~");}public String getBrand() {return brand;}public void setBrand(String brand) {this.brand = brand;}public String getColor() {return color;}public void setColor(String color) {this.color = color;}public int getId() {return id;}public void setId(int id) {this.id = id;}public double getPrice() {return price;}public void setPrice(double price) {this.price = price;}
}//4.创建子类
class BMW extends Car{String color = "五彩斑斓的黑";//5.重写父类的方法@Overridepublic void start(){System.out.println("都让开,我的车要起飞啦~");}
}
//6.创建子类2
class TSL extends Car{//7.重写父类的方法@Overridepublic void stop(){System.out.println("唉呀妈,怎么停不下来呢");}//8.添加子类的特有功能public void swim(){System.out.println("没想到吧,我还是个潜水艇");}
}

7.2 多态为了统一调用标准

package cn.tedu.oop2;public class TestFruit {public static void main(String[] args) {Fruit f = new Fruit();Apple a = new Apple();Orange o = new Orange();get(f);get(a);get(o);}//只需要创建一个方法,就可以执行截然不同的效果//忽略子类对象的差异统一看作父类类型public static void get(Fruit f){f.clean();}
}
class Fruit{public void clean(){System.out.println("水果要洗洗再吃");}
}
class Apple extends Fruit{@Overridepublic void clean(){System.out.println("苹果需要削皮");}
}
class Orange extends Fruit{@Overridepublic void clean(){System.out.println("橙子需要剥皮");}
}

7.3 静态变量和实例变量的区别

在语法定义上的区别:静态变量前要加static关键字,而实例变量前则不加。
在程序运行时的区别:实例变量属于某个对象的属性,必须创建了实例对象,其中的实例变量才会被分配空间,才能使用这个实例变量。静态变量不属于某个实例对象,而是属于类,所以也称为类变量,只要程序加载了类的字节码,不用创建任何实例对象,静态变量就会被分配空间,静态变量就可以被使用了。总之,实例变量必须创建对象后才可以通过这个对象来使用,静态变量则可以直接使用类名来引用。

7.4 向上转型和向下转型

在JAVA中,继承是一个重要的特征,通过extends关键字,子类可以复用父类的功能,如果父类不能满足当前子类的需求,则子类可以重写父类中的方法来加以扩展。
那么在这个过程中就存在着多态的应用。存在着两种转型方式,分别是:向上转型和向下转型。
向上转型:可以把不同的子类对象都当作父类来看,进而屏蔽不同子类对象之间的差异,写出通用的代码,做出通用的编程,统一调用标准。
比如:父类Parent,子类Child
父类的引用指向子类对象:Parent p=new Child();
说明:向上转型时,子类对象当成父类对象,只能调用父类的功能,如果子类重写了父类中声明过的方法,方法体执行的就是子类重过后的功能。但是此时对象是把自己看做是父类类型的,所以其他资源使用的还是父类型的。
比如:花木兰替父从军,大家都把花木兰看做她爸,但是实际从军的是花木兰,而且,花木兰只能做她爸能做的事,在军营里是不可以化妆的。

向下转型(较少):子类的引用的指向子类对象,过程中必须要采取到强制转型。这个是之前向上造型过的子类对象仍然想执行子类的特有功能,所以需要重新恢复成子类对象
Parent p = new Child();//向上转型,此时,p是Parent类型
Child c = (Child)p;//此时,把Parent类型的p转成小类型Child
其实,相当于创建了一个子类对象一样,可以用父类的,也可以用自己的
说明:向下转型时,是为了方便使用子类的特殊方法,也就是说当子类方法做了功能拓展,就可以直接使用子类功能。
比如:花木兰打仗结束,就不需要再看做是她爸了,就可以”对镜贴花黄”了


http://chatgpt.dhexx.cn/article/aPrL89BL.shtml

相关文章

html表单实例:用户反馈表单页面代码

<!DOCTYPE html> <html lang"en"> <head><meta charset"UTF-8"><title>demo</title> </head> <body><h1 align"center">用户反馈表单</h1><form method"post"><…

html 下拉多选框代码,js实现下拉复选框效果(代码实例)

本章给大家带来用js实现下拉复选框效果(代码实例),有一定的参考价值,有需要的朋友可以参考一下,希望对你有所帮助。 先看看效果: 下面我们看看代码: HTML代码: HTMLCSSJavaScriptjQueryPHPMySQLJavaC#C++Pyhtoncss代码:div {display: inline-block; } select {min-width…

HTML实例--制作表单

运用表格和表单基础知识简单制作一个表单 表单制作使用表格来对表单进行排版美化 <!DOCTYPE html> <html lang"en"> <head><meta charset"UTF-8"><meta http-equiv"X-UA-Compatible" content"IEedge">…

Html5 Canvas绘图实例

前些年的时候&#xff0c;突然对Canvas感兴趣&#xff0c;利用空闲时间做一些Canvas小例子进行练习&#xff0c;仅供学习分享使用。如有不足之处&#xff0c;还请指正。 什么是 Canvas&#xff1f; HTML5 的 canvas 元素使用 JavaScript 在网页上绘制图像。画布是一个矩形区域…

用html做个随机点名系统代码,html座位表随机点名的实例代码

这篇文章详解html座位表随机点名的实例代码点名 td { width: 9.09%; height: 50px; text-align: center; } .tdBg { background-color: pink; } var timer null; // 这是一个函数&#xff0c;表示一个功能 function start(){ timer setInterval(function(){ // alert("要…

在html中如何写日期的代码,日期html代码

日期 时间 星期的html代码是什么代码 创建静态方法findDate,返回List类型。 声明一个List list集合,向List集合存储英文星期。 调用findDate静态方法,并打印List集合存储结果。 CSS布局HTML小编今天和大家分享一个显示当前系统日期的HTML代码 显示的格式为“某年某月某日”,…

html向上移动图片代码,图片随网页上下移动的代码实例

我们以腾讯QQ网页在线客服为例,大家将代码拷到DW中,用心体会。图片随网页上下移动的代码实例 function picsize(obj,MaxWidth){img=new Image(); img.src="/obj.src"; if (img.width>MaxWidth) {return MaxWidth; } else {return img.width; } } function Close…

html5 简单实例源代码

实例教程&#xff1a;http://www.w3school.com.cn/jquery/ 源代码下载&#xff1a; http://download.csdn.net/detail/wyx100/9827067 html5文件布局结构 html5文件布局结构html5语言标记 浏览器执行效果 html5文件源代码 源代码下载&#xff1a; http://download.csdn.net/de…

html实例,实现表单

1.使用HTML完成下列功能 <!doctype html> <html><head><!-- <meta charset"GBK">--></head><body><table width"60%" border"3" align"center" bgcolor"#F0F8FF" borderColor…

html导航栏纵向代码,html横向导航栏怎么做?横向导航条代码实例

有不少小伙伴在刚学习 html 的时候都会遇到这样一个问题&#xff1a;html 横向导航栏怎么做&#xff1f;今天W3Cschool小编就为大家分享一下简单的横向导航条代码&#xff0c;相信会对大家有所帮助。 html 横向导航栏一般用两种方法来制作&#xff1a;第一种&#xff0c;我们使…

html如何插入下拉菜單,html下拉菜单怎么做?html下拉菜单的代码实例介绍

本篇文章主要的介绍了关于HTML select标签下拉菜单的做法实例&#xff0c;还有一个html的一些网站的下拉菜单的用法都放在了文章中&#xff0c;下面就让我们一起来看看这篇文章吧 首先我们要知道html下拉菜单的代码是什么&#xff1f; 很明显是select元素可创建单选或多选菜单。…

HTML代码示例和介绍

HTML基本的格式 <!DOCTYPE html> <!-- 声明文档。定义html --> <html lang"en"> <!-- 元素是页面的根元素 --> <head> <!-- 元素包含文档的元数据 --><meta charset"UTF-8"&g…

STM32仿真器下载程序出现SWD/JTAG Communication Failure的解决方法

一、解决办法&#xff1a;将STM32开发板断电&#xff0c;将板子上的BOOT0用短路帽接入3.3V高电平&#xff0c;重新插入仿真器&#xff0c;下载程序到开发板。不出意外可见程序烧录成功&#xff0c;此时将BOOT0接回低电平&#xff0c;后续烧录程序便不会出现SWD/JTAG Communicat…

keil无法识别JTAG仿真器解决办法

一、操作步骤 1、操作环境&#xff1a; 开发板&#xff1a;野火STM32H743XI 电脑系统版本&#xff1a;Windows 10 专业版 使用笔记本调试 JTAG&#xff1a;Fire-Debugger 野火 高速版DAP编程器 2、操作步骤&#xff1a; 将JTAG连接在STM32调试接口和电脑USB接口上&#xff0c…

JTAG调试原理

转自&#xff1a;https://blog.csdn.net/sinat_24088685/article/details/50980501 1.介绍 JTAG&#xff08;Joint Test Action Group&#xff0c;联合测试行动小组&#xff09; 是一种 国际标准测试 协议&#xff0c;主要用于 芯片内部测试 。现在多数的高级器件都支…

MCU模拟JTAG接口对LATTICE CPLD FPGA 进行在线编程加载

完整版请点击 https://hifpga.com/问题/719 索取源码&#xff0c;向博主本人提问FPGA相关问题 作者&#xff1a;Rock.Ding&#xff08;莱迪思半导体公司&#xff09;关键字&#xff1a;MCU, JTAG, 在线编程, CPLD。 前言 CPLD(Complex Programmable Logic Device)复杂可编程…

JTAG+SWD在Keil5中进行仿真

JTAGSWD在Keil5中进行仿真 上一章说了STM32的烧录问题&#xff0c;主要有slink、TTL-usb的方法&#xff0c;通过相应的烧录软件&#xff0c;进行一个下载烧录的过程&#xff0c;用到的模式也主要是SWD的模式&#xff0c;毕竟只有四根线比较方便。 这篇主要是仿真测试&#xff…

【开发工具】【JTAG】JTAG调试原理【二】

相关链接&#xff1a; JTAG基础 JTAG调试原理 JTAG调试实例 模拟系统崩溃&#xff0c;使用JTAG调试找到崩溃点 JTAG调试原理 两个重要概念&#xff1a;边界扫描和TAP 边界扫描 JTAG如何用于芯片测试呢&#xff1f; 其中用到的最主要部件就是边界扫描链。 边界扫描&…

STM32中使用J-Link仿真器选择JTAG模式和SWD模式的区别

0. 下载调试器(仿真器) 下载调试器是将PC(例如通过USB协议)发送的命令转换为MCU(负责MCU内部外围设备)理解的语言(例如SWD或JTAG协议)的设备&#xff0c;加载代码并精确控制执行。 1. J-Link J-Link是SEGGER公司为支持仿真ARM内核芯片推出的JTAG/SWD仿真器。配合IAR EWAR&am…

ARM JTAG仿真器电路讨论

一. JTAG仿真器的实质 JTAG (Joint Test Action Group) 编程调试实质上是利用了MCU/MPU片上自带的跟踪调试功能&#xff08;需MCU/MPU硬件支持&#xff09;。JTAG编程板一端与PC的并口相连&#xff0c;另一端连接至目标板&#xff0c;由于通常的MCU/MPU的工作电压在1.8V…