java 多态判断非空_Java核心技术(四):继承

021d52679516b930a6f070ca43f1a5c7.png

本章目录:

  • 一、类、超类和子类
  • 1.多态
  • 2.动态绑定
  • 3.阻止继承:final类和方法
  • 4.抽象类
  • 5.访问修饰符总结
  • 二、Object类:所有类的父类
  • 1.equals方法
  • 2.hashcode方法
  • 3.toString方法
  • 三、对象包装器与自动装箱
  • 四、反射
  • 1.Class类
  • 2.捕获异常
  • 3.利用反射分析类的能力
  • 4.在运行时使用反射分析对象

一、类、超类和子类

  • 子类继承父类,二者之间是is-a关系,子类拥有父类的全部资源,并且可以添加特有的域和方法。
  • 子类无法删除。
  • java不支持多继承。
  • 子类可重写父类的方法,注意,重写和方法重载是不同的概念。 在覆盖(重写)一个方法的时候,子类方法不能低于超类方法的可见性。特别是,如果超类方法是 public,子类方法一定要声明为 public。
  • 子类如何调用父类方法:super.父类方法名()。
  • 子类构造器中如何调用父类构造器:super.父类名(参数列表),注意,这句代码必须在子类构造器中的第一句。
如果子类的构造器没有显式地调用超类的构造器,则将自动地调用超类默认(没有参数)的构造器。
如果超类没有不带参数的构造器,并且在子类的构造器中又没有显式地调用超类的其他构造器,则 Java 编译器将报告错误。
  • 多态:一个对象变量可以指示多种实际类型的现象被称为多态。在运行时能够自动地选择调用哪个方法的现象称为动态绑定。

1.多态

  • 在 Java程序设计语言中,对象变量是多态的。一个父类变量既可以引用一个父类对象,也可以引用任何一个子类的对象。
  • 然而,不能将一个父类的引用赋给子类变量。
  • 警告∶ 在 Java中,子类数组的引用可以转换成超类数组的引用,而不需要采用强制类型转换。例如,下面是一个经理数组

2.动态绑定

前面已经说过了,一个对象变量可以指示多种实际类型的现象被称为多态,在运行时能够自动地选择调用哪个方法的现象称为动态绑定。

下面请看调用方法的过程:

  • 编译器查看对象的声明类型和方法名。假设调用x.f(param),且隐式参数x声明为C类的对象。需要注意的是∶ 有可能存在多个名字为f,但参数类型不一样的方法。编译器将会一一列举所有C类中名为f的方法和其超类中访问属性为 public 且名为f的方法(超类的私有方法不可访问)。至此,编译器已获得所有可能被调用的候选方法。
  • 重载解析:接下来,编译器将查看调用方法时提供的参数类型。如果在所有名为f的方法中存在一个与提供的参数类型完全匹配,就选择这个方法。这个过程被称为重载解析。由于允许类型转换(int 可以转换成 double,Manager类可以转换成 Employee;类,等等),所以这个过程可能很复杂。如果编译器没有找到与参数类型匹配的方法,或者发现经过类型转换后有多个方法与之匹配,就会报告一个错误。至此,编译器已获得需要调用的方法名字和参数类型。
不过,返回类型不是签名的一部分,因此,在覆盖方法时,一定要保证返回类型的兼容性。允许子类将覆盖方法的返回类型定义为原返回类型的子类型。例如,假设
  • 如果是 private 方法、static方法、final方法或者构造器,那么编译器将可以准确地知道应该调用哪个方法,我们将这种调用方式称为静态绑定。
  • 当程序运行,并且采用动态绑定调用方法时,虚拟机一定调用与x所引用对象的实际类型最合适的那个类的方法。否则,将在D类的超类中寻找该方法,以此类推。

每次调用方法都要进行搜索,时间开销相当大。因此,虚拟机预先为每个类创建了一个方法表,其中列出了所有方法的签名和实际调用的方法。

这里需要提醒一点,如果调用super.f(param),编译器将对隐式参数超类的方法表进行搜索。

3.阻止继承:final类和方法

用 final修饰的类是禁止继承的;用final修饰的方法,则表明该方法不允许类的子类重写;final类中的所有方法默认为是final方法。

在早期的Java中,有些程序员为了避免动态绑定带来的系统开销而使用final关健字。如果一个方法没有被覆盖并且很短,编译器就能够对它进行优化处理,这个过程为称为内联。例如,内联调用e.getName()将被替换为访问e.name域。然而,如果getName()在另外一个类中被覆盖,那么编译器就无法知道覆盖的代码将会做什么操作,因此也就不能对它进行内联处理了。

幸运的是,虚拟机中的即时编译器比传统编译器的处理能力强得多。这种编译器可以准确地知道类之间的继承关系,并能够检测岀类中是否真正地存在覆盖给定的方法。如果方法很简短、被频繁调用且没有真正地被覆盖,那么即时编译器就会将这个方法进行内联处理。如果虚拟机加载了另外一个子类,而在这个子类中包含了对内联方法的覆盖,那么将会发生什么情况呢?优化器将取消对覆盖方法的内联。这个过程很慢,但却很少发生。

4.抽象类

为了提高程序的清晰度,包含一个或多个抽象方法的类本身必须被声明为抽象的。

abstract class Person{……public abstract String getDescription();
}
  • 除了抽象方法之外,抽象类还可以包含具体数据和具体方法。但尽量使得抽象类中不包含具体方法。
  • 抽象方法充当着占位的角色,它们的具体实现在子类中。不过,在子类中定义部分抽象方法或抽象方法也可以不定义,这样就必须将子类也标记为抽象类。
  • 类即使不含抽象方法,也可以将类声明为抽象类。
  • 抽象类不能被实例化;可以定义一个抽象类的对象变量,但是它只能引用非抽象子类的对象。

5.访问修饰符总结

  • 对本类可见private
  • 对所有类可见public
  • 对本包和所有子类可见protected
  • 默认本包可见

二、Object类:所有类的父类

可以使用Object类型的变量引用任何类型的对象。

1.equals方法

检测一个对象和另一个对象是否相等,用于判断两个对象是否具有相同的引用。

在子类中定义 equals 方法时,首先调用超类的 equals。如果检测失败,对象就不可能相等。如果超类中的域都相等,就需要比较子类中的实例域。

Java中的equals方法具有以下特性:

  • 自反性∶ 对于任何非空引用x,x.equals(x)应该返回 true。
  • 对称性∶ 对于任何引用x和y,当且仅当yequals(x)返回true,x.equals(y)也应该返回 true。如果x和y不属于同个类,可能不适用。
  • 传递性∶对于任何引用x、y和z,如果x.cquals(y)返回true,yequals(z)返回true, x.equals(z)也应该返回 true。
  • 一致性∶如果x和y引用的对象没有发生变化,反复调用x.equals(y)应该返回同样的结果。
  • 对于任意非空引用x,x.equals(null)应该返回 false。

2.hashcode方法

散列码是由对象导出的一个整型值。散列码是没有规律的。如果x和y是两个不同的对象,x.hashCode()与y.hashCode()基本上不会相同。在表5-1中列出了几个通

3.toString方法

三、对象包装器与自动装箱

  • 对象包装器:

所有的基本类型都有一个与之对应的类。这些类称为包装器∶Integer、Long、Float、Double、Short、Byte、Character、Void和 Boolean(前 6个类派生于公共的超类 Number)。对象包装器类是不可变的,即一旦构造了包装器,就不允许更改包装在其中的值。同时,对象包装器类还是 final,因此不能定义它们的子类。

泛型是能是引用类型而不能是基本类型。

  • 自动装箱:

list是一个集合对象,list.add(3)将自动地变换成list.add(Integer.valueOf(3)。这一过程就是自动装箱。
int n= list.get(i)将自动被翻译成int n=list.get(i).intValue()。这一过程就是自动拆箱。

最后强调一下,装箱和拆箱是编译器认可的,而不是虚拟机。编译器在生成类的字节码时,插入必要的方法调用。虚拟机只是执行这些字节码。

四、反射

1.Class类

在程序运行期间,保存对象的运行时类型信息的类被称为 Class。

Employee e;……Class c1=e.getClass();//获取Class对象String classType=c1.getName();//获取e的类名,包含了包前缀String name=e.getName();//获取e的对象名Class c2=Class.forName(classType);//也可通过已知的类名获取Class对象Class c3=Date.class;//也可通过这种方式获取类对象Class c4=int.class;CLass c5=Double[].class;Object o=e.getClass().new Instance();//创建一个和e同类型的实例,调用的是默认构造器

2.捕获异常

try{//可能抛出异常的语句}catch(Exception e){//处理器语句}

一旦try中出现异常,将跳过剩余的部分,直接进入catch中进行处理;若try中没有出现异常,则跳过catch中的部分。

3.利用反射分析类的能力

说白了就是通过调用Class类中的方法得到关于所涉及对象的域、方法、构造器、访问权限修饰符相关的信息,这部分学习下Java API中有关Class的部分就好。

4.在运行时使用反射分析对象

在代码运行时获取到对象的状态等。好好看看API。

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

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

相关文章

互相引用 spring_听说你还不知道Spring是如何解决循环依赖问题的?

作者:Vt前言Spring如何解决的循环依赖,是近两年流行起来的一道Java面试题。其实笔者本人对这类框架源码题还是持一定的怀疑态度的。如果笔者作为面试官,可能会问一些诸如“如果注入的属性为null,你会从哪几个方向去排查”这些场景…

打印多页时两边取消留白_办公必备技巧:Word打印技巧大全

打印是每一位办公族都要掌握的一项最基础的技能。平常在用WORD写作、对文章进行排版等,最终我们都是需要将其打印到纸张上。在打印中有着众多的操作技巧,如果你还不会,那今天易老师就来给你科普一下。本文目录第一部分:基础打印操…

中raise抛出异常_Python 异常处理知识点汇总,五分钟就能学会 !

异常处理在任何一门编程语言里都是值得关注的一个话题,良好的异常处理可以让你的程序更加健壮,清晰的错误信息更能帮助你快速修复问题。在Python中,和不分高级语言一样,使用了try/except/finally语句块来处理异常,如果…

python中print语法错误_Python 3.x中使用print函数出现语法错误(SyntaxError: invalid syntax)的原因...

在安装了最新版本的Python 3.x版本之后,去参考别人的代码(基于Python 2.x写的教程),去利用print函数,打印输出内容时,结果却遇到print函数的语法错误:SyntaxError: invalid syntax这是因为Python 2.x升级到Python 3.x&…

easyexcel多个sheet导入_Java中Easypoi实现excel多sheet表导入导出功能

Easypoi简化了开发中对文档的导入导出实现,并不像poi那样都要写大段工具类来搞定文档的读写。第一步引入Easypoi依赖cn.afterturneasypoi-spring-boot-starter4.2.0Easypoi的注解使用说明(存留查看即可)第二步定义对应表格头数据对象实体类(注解的使用可以查阅上面的…

mysql 严格模式_MySQL 开启/关闭 严格模式(Strict Mode)

[广告:最高 2000 红包]阿里云服务器、主机等产品通用,可叠加官网常规优惠使用 | 限时领取查看 Mysql 是否开启严格模式:打开 MySQL 配置文件 my.cnf(windows为my.ini)。搜索 sql-mode 如果搜索不到就代表 非严格模式 。搜索到了就代表开启了严…

mysql 导入日期 0000_解决Excel导入MySQL日期为0000-00-00

最近在为客户做一个库存升级改造的项目,之前客户的数据管理全部是在Excel中操作,估计以前也是没有意识到数据量变大以后,工作会变得如此困难,基本上处于一个无法操作的程度了。于是我们将旧版本的Excel表格格式化以后,…

关于mysql优化_关于MySQL优化的几点总结

前言现如今,数据库的操作越来越成为整个应用的性能瓶颈了,这点对于Web应用尤其明显。所以,我整理了MySQL优化的几点建议,希望这些优化技巧对您有用,总结不到的,欢迎大家补充。SQL执行慢的原因网络速度慢&am…

ubuntu忘记mysql密码_ubuntu 忘记mysql 密码解决方法

一段时间没有用mysql数据库,今天突然需要使用,结果忘记密码,google了下找到的解决方法,就顺便记录下,下次碰到就不需要这么麻烦了1、输入命令 cat /etc/mysql/debian.cnf2、使用账号 debian-sys-maint 账号登录mysql密…

navicat mysql创建表_Navicat for MySQL如何创建数据表

Navicat for MySQL是针对MySQL数据库管理而研发的管理工具,创建数据表是其最基本操作,本教程将详解Navicat for MySQL创建数据表的方法。 步骤一:新建连接 运行Navicat数据库管理工具,连接本地数据库。点击左上角“文件”或者工具栏“连接”图标,创建自己的数据库连接。Na…

python mysql dbutils_python操作mysql数据库增删改查的dbutils实例

#encodingutf-8importMySQLdbimportgconf#主类classMysqlConnection(object):def __init__(self, host, port, user, passwd, db, charsetutf8):self.__host hostself.__port portself.__user userself.__passwd passwdself.__db dbself.__charset charsetself.__conn Noneself…

abp mysql .net core_ABP Asp.Net Core 集成 MySql 数据库

ASP.NET Boilerplate(简称ABP)是.Net平台下一个很流行的DDD框架,该框架已经为我们提供了大量的函数,非常方便与搭建企业应用。官方文档:http://www.aspnetboilerplate.com/Pages/DocumentsABPEFSQL Server是比较推荐的组合,由于使…

jboss mysql驱动目录_找不到mysql.jdbc.Driver – MySQL,JBoss

我无法将我的Web应用程序与MySQL 5.5.11后端部署到JBoss 5.我收到此错误:引起:java.lang.ClassNotFoundException:来自BaseClassLoader 262b2310的com.mysql.jdbc.Driver我在下面粘贴了我的堆栈跟踪.这就是我所做的……我将mysql-connector-…

mysql-5.1.73-8.el6_在centos中安装mysql详细步骤说明

Last login: Sun Dec 24 04:55:59 20171、安装依赖[rootnode001 ~]# yum install -y perlLoaded plugins: fastestmirrorLoading mirror speeds from cached hostfilebase | 3.7 kB 00:00extras | 3.4 kB 00:00updates | 3.4 kB 00:00Setting up Install ProcessPackage 4:perl…

mysql视图存储_Mysql 视图、存储过程以及权限控制

导读:该文章为视图、存储过程、用户权限练习;如果有不对的地方欢迎指出与补充;该基础练习基于MySQL5.0以上;语句格式:1. 视图格式:create view view_name[列名,列名.....] as select 子查询 wit…

21天学MySQL_SQL21天自学通.pdf

SQL21天自学通SQL 21 日自学通(V1.0) 翻译人 笨猪目录目录 1译者的话 14第一周概貌 16从这里开始 16第一天 SQL 简介 17SQL 简史 17数据库简史 17设计数据库的结构 21SQL 总览 23流行的SQL 开发工具 24SQL 在编程中的应用 27第二天 查询— — SELECT 语句的使用 30目标 30背景 …

lte盲重定向_LTE重选、切换、重定向的区别

【资料名称】:LTE重选、切换、重定向的区别【资料作者】:A【资料日期】:20150916【资料语言】:中文【资料格式】:DOC/DOCX【资料目录和简介】:这里主要简单阐述了LTE系统的小区重选、切换、重定向的区别小区…

冯乐乐 unity_Unity常用矩阵运算的推导补遗——切线空间

在上一篇文章中,我写了一些关于Unity中各个坐标空间及其转换矩阵是如何得到的,说实在的,我是那种“记忆需要依靠外部装置存储”类、如同《攻壳机动队》的电子脑一样的人,每次遇到问题了再去对着笔记慢慢翻找才是我的风格&#xff…

mysql 字段类型设计_Mysql字段类型设计相关问题!-阿里云开发者社区

Mysql是以文件存储在我们的系统的硬盘上面,那么(1)当我们读取写入的时候就会有磁盘IO的问题(2)当我们存储的数据是以页单位存储,而且每页的大小是16K,那么我们要尽可能的让我们的一页数据存放的更多。表结构宽度不要太大,也就是列…

mysql保存时乱码了_MySQL保存中文乱码的原因和解决办法

(3)MySQL的字符集设置。这个是重点了,一般都是在这里搞错而出现了mysql乱码。mysql编码设置可以分为三种设置:数据库的编码、表的编码、和字段的编码。a、数据库的编码:在sqlyog工具中操作把,右击数据库点击更改数据库&#xff0c…