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

新手小白学JAVA 面向对象之多态4多态4.1概念多态指同一个实体同时具有多种形式它是面向对象程序设计(OOP)的一个重要特征。主要是指同一个对象,在不同时刻,代表的对象不一样,指的是对象的多种形态。好处是:可以把不同的子类对象都当作父类来看,可以屏蔽不同子类对象之间的差异,写出通用的代码,做出通用的编程,统一调用标准。水果有两种形态:水果和苹果,不关心买回来的是苹果还是西瓜,只要是水果就行classAnimal{//1.定义父类Animal…eat(){syso(“吃啥都行”)}}classCatexte

大家好,又见面了,我是你们的朋友全栈君。

多态

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添加重写的方法
@Override
public 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定义父类的静态方法play
public static void play(){ 

System.out.println("玩啥都行~");
}
}
//2.创建子类
class Dog2 extends Animal2{ 

//5.定义子类的成员变量
int sum = 20;
//6.重写父类的方法
@Override
public 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());//null
c.start();
c.stop();
//c.swim();//报错,父类对象不可以调用子类的特有功能
//10.创建纯纯的子类对象做测试
BMW b = new BMW();
System.out.println(b.color);//五彩斑斓的黑
System.out.println(b.getColor());//null
b.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.重写父类的方法
@Override
public void start(){ 

System.out.println("都让开,我的车要起飞啦~");
}
}
//6.创建子类2
class TSL extends Car{ 

//7.重写父类的方法
@Override
public 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{ 

@Override
public void clean(){ 

System.out.println("苹果需要削皮");
}
}
class Orange extends Fruit{ 

@Override
public 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
其实,相当于创建了一个子类对象一样,可以用父类的,也可以用自己的
说明:向下转型时,是为了方便使用子类的特殊方法,也就是说当子类方法做了功能拓展,就可以直接使用子类功能。
比如:花木兰打仗结束,就不需要再看做是她爸了,就可以”对镜贴花黄”了

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。

发布者:全栈程序员-用户IM,转载请注明出处:https://javaforall.cn/161937.html原文链接:https://javaforall.cn

【正版授权,激活自己账号】: Jetbrains全家桶Ide使用,1年售后保障,每天仅需1毛

【官方授权 正版激活】: 官方授权 正版激活 支持Jetbrains家族下所有IDE 使用个人JB账号...

(0)
blank

相关推荐

  • byte类型取值范围以及溢出详解

    byte类型取值范围以及溢出详解例1:publicclasstest{ publicstaticvoidmain(String[]args){ bytea=127; a=(byte)(a+3); System.out.println(a); }}输出-126,为什么呢byte类型的取值范围是-128-127这个输出结果是由java编码方式决定的,Java中正数用原码

  • win10下安装PyCharm以及激活

    win10下安装PyCharm以及激活【在此之前先安装好python】1.PyCharm是什么?PyCharm是一种PythonIDE,带有一整套可以帮助用户在使用Python语言开发时提高其效率的工具。PyCharm拥有一般IDE具备的功能,比如,调试、语法高亮、Project管理、代码跳转、智能提示、自动完成、单元测试、版本控制另外,PyCharm还提供了一些很好的功能用于Django开发,同时支持Google…

  • nuget无法下载_百度云下载慢的最佳解决办法

    nuget无法下载_百度云下载慢的最佳解决办法解决NuGet下载太慢的问题

  • matlab产生高斯白噪声

    matlab产生高斯白噪声函数介绍matlab里和随机数有关的函数:(1)rand:产生均值为0.5、幅度在0~1之间的伪随机数。(2)randn:产生均值为0、方差为1的高斯白噪声。(3)randperm(n):产生1到n的均匀分布随机序列。(4)normrnd(a,b,c,d):产生均值为a、方差为b大小为cXd的随机矩阵。rand:返回一个在区间(0,1)内均匀分布的随机数。rand(n):生成0到1之间的n阶(n×n)随机数方阵。rand(m,n):生成0到1之间的m×n的随机数矩阵。

    2022年10月21日
  • pycharm2020.2永久激活码(JetBrains全家桶)

    (pycharm2020.2永久激活码)最近有小伙伴私信我,问我这边有没有免费的intellijIdea的激活码,然后我将全栈君台教程分享给他了。激活成功之后他一直表示感谢,哈哈~https://javaforall.cn/100143.htmlIntelliJ2021最新激活注册码,破解教程可免费永久激活,亲测有效,上面是详细链接哦~0E14…

  • Oracle数据库之SQL语句练习篇–准备

    Oracle数据库之SQL语句练习篇–准备

发表回复

您的电子邮箱地址不会被公开。

关注全栈程序员社区公众号