JAVA-初步认识-第八章-继承-子父类中成员函数特点-覆盖
一.
讲述完成员变量,开始讨论一下成员函数在子父类中的特点。(还要复习不同函数的区别,以及为什么会有这样的区别?)
子类继承父类,而且不是私有的,都可以直接拿过来用。
对程序在内存中的运算过程,进行一个讲解。
先是主函数main和引用变量z加载入栈中,接着创建Zi类的对象,由于Zi类继承了Fu类,因此父类先加载。类是加载入方法区的,先是加载构造函数,然后加载show1()方法。然后加载Zi类,也是加载入构造函数Zi(),一般函数show2(),由于是有继承关系,存在一个super关键字,指向父类。
紧接着,堆内存中new一个Zi类对象,对象建立完之后,将地址编号赋值给引用变量z,完成z指向对象。
往下就是执行z.show1()和z.show2(),对象调用方法。由于对象是根据Zi类创建的,那么z.show1()在执行时,就是在子类中寻找有没有show1()方法,肯定是先找自己。一找,没有,接下来,就跟着super到父类中寻找,找到show1(),show1()就进栈,接着运行了。到第三句,对象调用show2()方法,去子类中找到了该方法,进栈运行就结束了。→这里还想插一句,关于子类内容和父类内容之间相互包含的问题。这个问题要从两个角度来分析,从代码上来看,符合继承关系的两个类之间,内容是完全不同的(从继承的定义来看,父类是从子类中抽取出来的,抽取之后,子类中就不存在该部分的内容,这部分内容单独成了一个类)。从背后的含义来看,虽然两个类的内容完全不同,但是子类是包含着父类的。
上面是对一般情况的描述,我们要着重讲解地是特殊情况。也就是两个类中有重名的方法。按照我们以前的知识来看,一个类中不可能存在相同声明的两个类,会存在调用不确定的问题。但是在子父类中可以存在相同声明的两个函数,为什么,因为它们有所属(虽然声明是一样的,但是存储的位置是不同的,那么这两个函数也就是不同的)。
按下图所示,如果执行语句中,调用的是show()方法,由于子类中自己有show(),那么直接调用就可以了,不需要再去父类中寻找了。
(这两个特性只有函数具有,重载的定义又忘记了。)
只有子类才能覆盖父类,
覆盖的意思是,就好像父类的方法被覆盖掉一样,其实没有覆盖,看着像。
这里还要插一句,应该来说不是每次创建对象都是采用的子类来作为对象的描述类的。还是说,由于是固定的继承关系,根据前期的分析整理,就保证了子类是包含有最大范围的内容,那么每次创建对象都是用子类来进行。
覆盖操作的注意事项:
必须要体现出子类和父类是一模一样,(这里的一样是指函数一样),函数一样是说返回值类型,函数名和参数列表,就是函数声明一致。(而重载是区分括号里的东西)
截图是什么意思呢?
目前我们学了三种权限,public,private,以及什么都没写的默认权限(前面什么权限修饰符都不写,本身也是一种权限)。当我们覆盖的时候,如果权限一致是可以的。如果父类里面加上了public,而子类中什么都没有,那么子类的权限就低于父类,这不合适(默认权限的大小是怎样的?),不能这样盖。DOS结果显示如下,就是说子类的权限太低了。这就是所说的覆盖权限不够,
如果子父类的权限都为public,这就是相等。如果父类中的函数为默认权限,子类为public权限,编译是没有问题的。
如果父类中是private权限,子类中是public权限。这个不叫覆盖,为什么呢?覆盖有这么一个特点,就是说父类有一个我可以用,但是我建立自己的,所以编译一个一模一样的,把你盖上,用我自己的,但是这里父类中的这个根本用不了。私有了,外面不知道,子类根本不知道父类有,不知道何谈覆盖呢。
覆盖是什么意思呢?子类不用的情况下,父类可以用。
当权限相同时,如果父类中又用static修饰,是怎么样呢?一编译,出错了。
紧接着又换了一种书写形式,子类为static修饰,父类没有,DOS结果显示,也是出错。上下两种情况不一样,一个是“被覆盖的方法”,另一个是“覆盖的方法”。
如果两边都加静态,就没问题了。DOS显示编译是可行的。
因此,注意事项如下。第二种很少见,到多态的时候,给大家讲解,为什么是这么一回事。对静态的方法而言,我们说的覆盖吧,并不是特别确切,因为它不再是依赖对象了,它依赖的是类。哪个类去用哪个内容。