Polymorphism[多态]

简述:

面向对象多态性指的是:发送消息给某个对象,让该对象自行决定响应何种行为。

通过将子类对象引用赋值给超类对象引用变量来实现动态方法调用

多态的三个前提条件:

  • 多态发生在有继承关系的类之间
  • 子类要对超类方法进行重写
  • 父类引用指向子类对象

要了解多态,先了解casting(对象转型)的概念。

Casting[对象转型]

1.基类的引用类型变量可以是指向子类的对象。

2.一个基类引用不能访问子类对象新增加的成员(属性和方法 )

3.可以使用引用变量instaceof来判断该引用类型变量所“指向”的对象是否属于该类,或者该类的子类。

4. 子类对象可以作为基类对象使用,称为(upcasting)“向上转型”,反之,基类对象当做来使用称为(downcasting)“强制转换”。

实例

我们创建两个类,并且有继承关系,一个Animal类和Cat类

class Animal{//每种动物都有名字public  String name;//对应初始化方法Animal(String name){this.name=name;}}
class Cat extends Animal{//猫眼睛的颜色public String eyesColor;//对应初始化Cat(String name,String eyesColor){super(name);this.eyesColor=eyesColor;}
}

然后我们在验证 "1.基类的引用类型变量可以是指向子类的对象"

public class Casting{public static void main(String[] args){System.out.println("-------------------------------");//创建Animal引用Animal coco=null;//把子类对象赋给父类引用coco=new Cat("mimi","black");//编译通过没问题
}

继续验证   "  2.一个基类引用不能访问子类对象新增加的成员(属性和方法  )  "

我们把两个类增加方法

class Animal{//每种动物都有名字public  String name;//对应初始化方法Animal(String name){this.name=name;}//动物叫声public void say(){System.out.println("name: "+name);}
}
//猫
class Cat extends Animal{//猫眼睛的颜色public String eyesColor;//对应初始化Cat(String name,String eyesColor){super(name);this.eyesColor=eyesColor;}public void miaow(){System.out.println("猫叫");}
}

我们用coco对象分别访问父类和子类的成员和方法

//coco调用Cat中所有的成员coco.name="mici";//可以访问子类继承到的name变量System.out.println(coco.name);//输出mici//coco.eyesColor="blue";/*编译输出:cannot find symbol说明父类引用看不到子类对象的成员,只能用父类Animal的视野看,那就只能看见name咯*/
        coco.say();//编译运行没问题
    //coco.miaow();/*编译输出:cannot find symbol同样是编译出错找不到成员,所以向上转型父类引用只能看见自己传下去的东西咯*/

先面我们來用 instanceof 来测试

首先

instanceof

instanceof是Java、php的一个二元操作符(运算符),和==,>,<是同一类东西。由于它是由字母组成的,所以也是Java的保留关键字。它的作用是判断其左边对象是否为其右边类的实例,返回boolean类型的数据。可以用在继承中的子类的实例是否为父类的实现。

应用于上面的例子

全部代码,做了修改

//Have the courage to follow your heart and intuition.
//对象转型。向上转型
//1.基类引用可以指向子类引用
//2.基类引用不能访问子类新增加的成员(方法属性)
//3.可以用 instanceof判断引用类型是不是这个类或者子类package me.animal;
class Animal{//每种动物都有名字public  String name;//对应初始化方法Animal(String name){this.name=name;}//动物叫声public void say(Animal any){System.out.println("name: "+any.name);//判断是什么类型猫啊狗啊,然后调用子类相应的成员if(any instanceof Cat){Cat cat=(Cat)any;System.out.println(" "+cat.eyesColor+" eyes");}else if(any instanceof Dog){Dog dog=(Dog)any;System.out.println(" "+dog.furColor+" fur");}}}
//猫
class Cat extends Animal{//猫眼睛的颜色public String eyesColor;//对应初始化Cat(String name,String eyesColor){super(name);this.eyesColor=eyesColor;}public void miaow(){System.out.println("猫叫");}
}
//狗
class Dog extends Animal{//狗毛的颜色public  String furColor;//对应初始化Dog(String name,String furColor){super(name);this.furColor=furColor;}//狗叫的方法public void bark(){System.out.println("狗叫了...");}}
public class Casting{public static void main(String[] args){System.out.println("-------------------------------");//创建Animal引用Animal coco=null;//把子类对象赋给父类引用coco=new Cat("mimi","black");//编译通过没问题//coco调用Cat中所有的成员coco.name="mici";//可以访问子类继承到的name变量System.out.println(coco.name);//输出micicoco.say();//编译运行没问题//coco.eyesColor="blue";/*编译输出:cannot find symbol说明父类引用看不到子类对象的成员,只能用父类Animal的视野看,那就只能看见name咯*///coco.miaow();/*编译输出:cannot find symbol同样是编译出错找不倒成员,所以向上转型父类引用只能看见自己传下去的东西咯*/coco.//创建猫狗对象System.out.println("-------------------------------");Cat nina=new Cat("nina","blue");Dog hasx=new Dog("hasx","black");Animal yoyo=new Animal("yoyo");//用instanceof判断是不是对象属于类型System.out.println("-------------------------------");System.out.println("nina instanceof Cat = "+(nina instanceof Cat));//tureSystem.out.println("nina instanceof Animal = "+(nina instanceof Animal));//true//System.out.println("hasx instanceof Cat = "+(hasx instanceof Cat));/* 这样编译错误:inconvertible types使用instanceof 前提必须要有继承关系,*/System.out.println("-------------------------------");System.out.println("hasx instanceof Dog = "+(hasx instanceof Dog));//trueSystem.out.println("hasx instanceof Animal = "+(hasx instanceof Animal));//true//动物引用yoyo 判断关系System.out.println("yoyo instanceof Animal = "+(yoyo instanceof Animal));//trueSystem.out.println("yoyo instanceof Cat = "+(yoyo instanceof Cat));//falseSystem.out.println("yoyo instanceof Dog = "+(yoyo instanceof Dog));//falseSystem.out.println("coco instanceof Animal = "+(coco instanceof Animal));//trueSystem.out.println("coco instanceof Cat = "+(coco instanceof Cat));//falseSystem.out.println("coco instanceof Dog = "+(coco instanceof Dog));//false/*这行编译没错而且可以运行,因为引用类型coco是Animal,还是与Dog有继承关系*/System.out.println("-------------------------------");//向下转型,Cat my=(Cat)coco;//my引用类型是猫,猫的成员当然可以访问咯System.out.println(my.eyesColor);my.miaow();//调用Animal创建的方法,可扩展行增强了System.out.println("-------------------------------");coco.say(coco);coco.say(nina);coco.say(hasx);coco.say(yoyo);System.out.println("-------------------------------");}

多态实例

经过上面对对象转型的认识,可以编写测试多态的代码

//一.多态测试
//多态三个条件:1.有继承 2.有重写 3.父类引用指向子类对象
package me.polymoph;//二.抽象方法就是用来重写的,1.继承下来的子类必须重写 2.抽象类不能不能new。3.//Final 1.Final的变量值不能改变 2.Final 的方法不能重写 3.Final的方法不能被继承
abstract class Animal{//~ public void enjoy(){//~ //动物高兴了叫//~ System.out.println("我叫叫叫~~");//~ }//抽象类改写abstract void enjoy();}
//子类
class Dog extends  Animal{//狗高兴不一定叫,我狗跳墙,复写方法public void enjoy(){System.out.println("我狗跳墙");}
}
class Cat extends Animal{//猫高兴了,走猫步,复写方法public void enjoy(){System.out.println("我走猫步");}}
class Wolf extends Animal{//狼高兴了,我吃兔子public void enjoy(){System.out.println("我吃兔子");}}//然后测试类
public class Polymoph{public static void main(String[] args){//创建动物对象,超类引用,赋予之类对象Animal coco=new Dog();//coco.enjoy();coco=new Cat();coco.enjoy();coco=new Wolf();coco.enjoy();/*输出:我狗跳墙我走猫步我吃兔子*///输出的是子类的方法}}

作者:YangGan

出处: http://blog.csdn.net/incyanggan

本文基于 署名 2.5 中国大陆 许可协议发布,欢迎转载,演绎或用于商业目的,但是必须保留本文的署名Yanggan (包含链接).

Java菜鸟学习笔记--面向对象篇(十八):对象转型多态相关推荐

  1. OpenCV学习笔记(五十六)——InputArray和OutputArray的那些事core OpenCV学习笔记(五十七)——在同一窗口显示多幅图片 OpenCV学习笔记(五十八)——读《Mast

    OpenCV学习笔记(五十六)--InputArray和OutputArray的那些事core 看过OpenCV源代码的朋友,肯定都知道很多函数的接口都是InputArray或者OutputArray ...

  2. OpenCV学习笔记(四十六)——FAST特征点检测features2D OpenCV学习笔记(四十七)——VideoWriter生成视频流highgui OpenCV学习笔记(四十八)——PCA算

    OpenCV学习笔记(四十六)--FAST特征点检测features2D 特征点检测和匹配是计算机视觉中一个很有用的技术.在物体检测,视觉跟踪,三维常年关键等领域都有很广泛的应用.这一次先介绍特征点检 ...

  3. OpenCV学习笔记(三十六)——Kalman滤波做运动目标跟踪 OpenCV学习笔记(三十七)——实用函数、系统函数、宏core OpenCV学习笔记(三十八)——显示当前FPS OpenC

    OpenCV学习笔记(三十六)--Kalman滤波做运动目标跟踪 kalman滤波大家都很熟悉,其基本思想就是先不考虑输入信号和观测噪声的影响,得到状态变量和输出信号的估计值,再用输出信号的估计误差加 ...

  4. OpenCV学习笔记(二十六)——小试SVM算法ml OpenCV学习笔记(二十七)——基于级联分类器的目标检测objdect OpenCV学习笔记(二十八)——光流法对运动目标跟踪Video Ope

    OpenCV学习笔记(二十六)--小试SVM算法ml 总感觉自己停留在码农的初级阶段,要想更上一层,就得静下心来,好好研究一下算法的东西.OpenCV作为一个计算机视觉的开源库,肯定不会只停留在数字图 ...

  5. 五子棋人机大战(Java菜鸟学习笔记)

    五子棋人机大战(Java菜鸟学习笔记) 逻辑是: 1.绘制棋盘: 2.人机开始各执行一次操作,每进行一次操作就进行判断输赢 其中判断输赢主要分成四个方向,横向.纵向以及交叉向,此时可以画图来找规律实现 ...

  6. Slicer学习笔记(二十八)Elastix扩展模块

    Slicer学习笔记(二十八)Elastix扩展模块 1.代码结构 1.1.代码结构 1.2.页面布局 1.3.Elastix路径选择 [可选] 2.执行配准 2.1 先去找到elastix.exe的 ...

  7. 【OS学习笔记】二十八 保护模式八:任务切换对应的汇编代码之内核代码

    本汇编代码对应以下两篇文章对应的内核汇编代码: OS学习笔记]二十六 保护模式八:任务门-任务切换 [OS学习笔记]二十七 保护模式八:任务切换的方法之----jmp与call的区别以及任务的中断嵌套 ...

  8. 【OS学习笔记】三十八 保护模式十:中断和异常的处理与抢占式多任务对应的汇编代码----微型内核汇代码

    本文是以下几篇文章对应的微型内核代码汇编代码: [OS学习笔记]三十四 保护模式十:中断和异常区别 [OS学习笔记]三十五 保护模式十:中断描述符表.中断门和陷阱门 [OS学习笔记]三十六 保护模式十 ...

  9. node JS獲取GPS_node学习笔记(三十八)

    一.什么是NodeJS? 1.Node.js 是一个基于 Chrome V8 引擎的 JavaScript 运行环境. 2.Node.js 使用了一个事件驱动.非阻塞式 I/O 的模型,使其轻量又高效 ...

  10. java学习笔记(二十八)——开发一个小项目(VMeeting3.0)

    上篇文章按照较规范的产品需求文档梳理了项目的逻辑,感觉开发起来明晰了很多:挂上一篇文章java学习笔记(二十七)--开发一个小项目(VMeeting2.0)_Biangbangbing的博客-CSDN ...

最新文章

  1. DELETE ADJACENT DUPLICATES FROM语句的深入研究及应用
  2. 目标检测评价标准 精准度(precision)、召回率(recall)、准确率(accuracy)、交除并(IoU)【全】
  3. 【译】zkSNARKs in a nutshell
  4. Android的debug.keystore拒绝访问导致的生成异常及解决方案
  5. 全套学习!mysql2003错误代码
  6. 台式机dp接口_精品导购:你想要的商务台式机 都在这里了!
  7. 汽车行业持续亏损?奥迪:不存在的
  8. werkzeug.local
  9. 谷歌开源 Python 代码漏洞查找工具 Atheris
  10. 洛谷——P1075 [NOIP2012 普及组] 质因数分解
  11. HAL中通过jni调用java方法的问题
  12. SQL Server性能常用语句
  13. 免疫算法(matlab)
  14. 金山词霸2005开启后导致桌面刷新的问题
  15. NEFU计算机组成原理课程设计之乘法器
  16. 计算机应用宣传传统文化,计算机应用工程系创建优秀传统文化特色班级侧记
  17. HDU--2015-TO-2019--假期实在是太无聊了....
  18. QML Qt.binding
  19. 优盘突然显示无法在此计算机,复制文件到U盘时突然无法复制提示磁盘被写保护该如何修复...
  20. MTI姿态传感器学习笔记

热门文章

  1. EGLImage使用记录
  2. CPU负载均衡之WALT学习
  3. Android tombstone文件是如何生成的
  4. 编程基础(一)——计算机中的数
  5. opencv函数介绍—normalize
  6. Ubuntu 16.04显示分辨率的更改
  7. SIP Servlet开发环境配置
  8. 2015年Java组B组
  9. 1949年-2021年历史县级行政区划分布数据 中国行政村边界数据、乡镇街道边界、行政区划边界
  10. 服务器上安装python anaconda最简明教程