深入java (类)对象初始化,类构造函数的调用以及多态(java中多态的实现机制以后补充)

来源:互联网 发布:淘宝导航尺寸是多少 编辑:程序博客网 时间:2024/06/04 01:04

上一篇文章初探类的加载和初始化顺序,这一篇文章继续总结在继承的场景中,我们构造对象的时候,构造方法的调用顺序(以及简单解释为什么会这样执行构造函数,这些构造函数的调用顺序一定是jvm里面的一些规则定下来的,其实这样的目的就是多态和其他(其他是什么我现在也不确定,满怀期待呀!!)),给自己解答当年的疑惑,对于虚拟机里面多态的实现机制,我们会在深入java虚拟机。原创不易,转载请注明出处:http://blog.csdn.net/yabay2208

一:创建类对象时构造函数的执行顺序

读大学的时候老师说的:当构造子类对象的时候,会先调用父类的构造函数,如果父类还有父类,那么会继续向上递归。
举例说明:
这里写图片描述
程序的运行结果:
这里写图片描述
现在我们探究一下为什么会有如此的的结果,读书的时候我就很好奇,现在弄懂了,希望能帮你一把。
当子类继承了父类之后,子类属性就有两个,分别是:double fortune和double myOwnWay,构造函数一般用于构造类对象的时候,为对象属性正确的赋值,所以当我们构造son类对象的时候,先向上执行father类的构造函数,可以正确初始化double fortune,接着继续执行son类的构造函数,初始化double myOwnWay。这样,我们就可以确保构造出的son对象所有的属性都可以得到正确的初始化了,可以确保构造出来的对象准确无误。补充一点:在java中,所有类的父类都是Object。用一张图来看一下:
这里写图片描述


二:多态

多态的用法很简单,这篇文章先简单说多态的用法跟要注意的一些基本的点,以后我们从jvm的角度探究java的多态机制是如何实现的,深入的文章写在《java深入jvm》。
看一个例子:我们先定义一个很简单父类:
这里写图片描述

定义其子类:
这里写图片描述

用父类句柄指向堆空间中的子类对象:
这里写图片描述

程序运行的结果是:
这里写图片描述
虽然都是Human作为句柄,但是我们在访问对象的Introduce()方法时,都正确的调用了对应的方法,这是一个实现多态的简单例子。

三:多态导致的访问空间的缩小和类型的擦除

1.我们在使用java这种很强大的多态特性的时候,有一点需要注意的就是多态带来的访问空间的缩小和类型擦除。我们还是举上一个例子说明问题。
访问空间的缩小问题:
这里写图片描述

访问的范围缩小为父类的范围:
这里写图片描述

运行结果:
这里写图片描述

2.使用多态导致的类型擦除:
这里写图片描述
当我们在ArrayList humanArrayList中取出第一个对象的时候,我们虽然知道这个对象其实就是Gay类的一个实例,但是编译器却不会让我们通过,因为向下转型可能出错。
当然这个时候我们可以强制转型为Gay类的一个对象:

Gay GayP2 = (Gay)humanArrayList.get(0);

但是这样做其实是有很大风险的,因为我们从humanArrayList中取出来的也有可能是Woman或者Man的对象,这样强制转型在编译器可以通过,但是在运行其很有可能会出现:java.lang.NullPointerException;更加安全的做法应该线检查一遍我们取出来的类型是否是我们要转型的一个实例:
这里写图片描述

多态基础先到这,系一篇文章我们从设计的角度理解抽象类和接口,并理解java为何不能实现多继承,接口为何可以继承多个接口。

1 0
原创粉丝点击