java的override和overload详解
来源:互联网 发布:类似变速齿轮的软件 编辑:程序博客网 时间:2024/06/08 02:37
在详解override和overload前需要对多态做一个详细的了解
什么是多态?
多态的教科书标准定义:允许不同类的对象对同一消息做出响应。即同一消息可以根据发送对象的不同而采用多种不同的行为方式。其实可以借助于生活中的常见的一种多态现象来解释多态:比方说按下 F1 键这个动作,如果当前在 Flash 界面下弹出的就是 AS 3 的帮助文档;如果当前在 Word 下弹出的就是 Word 帮助;在 Windows 下弹出的就是 Windows 帮助和支持。同一个事件发生在不同的对象上会产生不同的结果。
实现多态的技术
在java中,实现多态的两种方式为override重写和overload重载,而最终实现的技术为:动态绑定(dynamic binding),指在执行期间判断所引用对象的实际类型,根据其实际的类型调用其相应的方法
多态->晚绑定
多态是一种运行期的行为,不是编译期的行为。
多态的方法访问原理
虽然说父类的引用指向的是子类的对象,但是最终该引用还是父类,当使用多态方式调用方法时,首先检查父类中是否有该方法,如果没有,则编译错误;如果有,就会去查找子类中是否有同名方法,如果没有,则调用父类的该方法;如果有,则会判断是否满足重写的两同两小一大原则,如果满足,则调用子类的该方法;如果不满足,则编译器报错;
多态访问的方法访问测试案例
//test1 子类中没有该同名方法class fun{ public void mi() throws NullPointerException{ System.out.println("fa mi ..."); }}public class overrideTest extends fun{ public static void main(String[] args) { fun f = new overrideTest(); f.mi(); }}//test1的最终输出结果为:fa mi... 调用的是父类的mi方法//test2 子类中重写了父类的方法class fun{ public void mi() throws Exception{ System.out.println("fa mi ..."); }}public class overrideTest extends fun{ public void mi() throws NullPointerException{ System.out.println("over mi..."); } public static void main(String[] args) throws Exception { fun f = new overrideTest(); f.mi(); }}//test2中因为子类有同名方法,并且满足两同两小一大原则,所以运行正常,输出 over mi..调用的是子类的mi方法//test3 子类有该同名方法,但是不满足override原则class fun{ public void mi() throws NullPointerException{ System.out.println("fa mi ..."); }}public class overrideTest extends fun{ public void mi() throws Exception{ System.out.println("over mi..."); } public static void main(String[] args) throws Exception { fun f = new overrideTest(); f.mi(); }}//test3中子类有该同名方法,但是不遵循重写原则(子类抛出的异常大于父类),因此在编译期就会进行报错//test4 父类中并没有该方法,但是子类中有该方法class fun{}public class overrideTest extends fun{ public overrideTest mi() throws NullPointerException{ System.out.println("over mi..."); return null; } public static void main(String[] args) throws Exception { fun f = new overrideTest(); f.mi(); }}//test4中程序也会在编译期报错,因为虽然父类的引用是指向子类的对象,但是最终还是父类类型引用,依旧是父类对象在进行调用,而在test4中父类并没有该方法,子类的方法只是属于子类,并不能扩展父类,所以将会报错
言归正传,现在来说说override和overload
override
重写,是子类对父类的特定方法一种修改,是父类和子类之间的多态的实现
override原则(两同两小一大)
两同:方法名相同,参数列表相同
两小:子类方法返回值小于等于父类;子类抛出的异常小于等于父类
一大:子类方法的修饰符访问权限大于等于父类
代码重点解析override原则->两小
首先我们来看,子类方法的返回值小于等于父类,这里注意的是,如果返回值是基本数据类型,就必须要相等;如果为引用类型的话,可以小于,即子类的返回类型可以是父类返回类型的子类,即在返回值上面进行了多态;
//测试方法返回值小于class fun{ protected fun mi() throws Exception{ System.out.println("fa mi ..."); return null; }}public class overrideTest extends fun{ public overrideTest mi() throws NullPointerException{ System.out.println("over mi..."); return null; } public static void main(String[] args) throws Exception { fun f = new overrideTest(); f.mi(); }}//代码运行正常
接下来我们来看看下一个:子类方法抛出的异常要小于等于父类,这是为什么呢,从一个很简单的方面进行解释:当我们定义一个需要抛出异常的方法时,我们在main方法(所有的方法)进行调用该方法时,都是需要抛出该方法对应的异常的,而因为引用类型是父类,所以最终main方法中抛出的异常是与父类的该方法一致的,而这个时候子类对该方法进行重写了,所以实质上调用的是子类的方法,如果这个时候子类抛出的异常范围大于父类时,那么就会导致异常捕获失败,不成立;因此,子类重写的方法抛出的异常是要小于等于父类的;
//代码和test相同,main中抛出的异常与fun.mi一致
代码重点解析override原则->一大
这里一大指的是:子类的方法访问权限要大于等于父类,试想一下,在运行时,我们真正调用的是子类重写后的方法,如果这个时候子类的方法我们没有权限,就只能访问父类的该方法了,从而不符合重写调用,不成立;所以子类的访问权限要大于等于父类的,目的是比父类原生方法有更大的权限进行调用,父类原生方法可以调用的地方都可以调用子类重写后的方法;
//代码同test4,父类使用protected、子类使用public进行修饰
overload重载
重载发生在一个类的内部,主要用于实现类对象的多态;
重载的原则
方法名必须相同;
参数列表必须不相同,参数列表或者参数个数任一个不同即可(参数之间为父子关系也算不同,int 和Integer也算不同)
方法的修饰符和返回值可以相同,也可以不相同;
代码重点解析overload原则
一个方法的定义,主要由:访问权限控制符+方法返回值+方法名+参数列表组成,对于重载来说,不管访问权限控制符和方法返回值是否相等,它都必须满足:方法名相同、参数列表不同,即使前面两者都不同,也需要满足这两个条件
//错误的重载public class overrideTest extends fun{ public overrideTest mi() throws NullPointerException{ System.out.println("over mi..."); return null; } private int a(String s){ //1. return 1; } public double a(String s){ //2. return 2; } public static void main(String[] args) throws Exception { overrideTest t = new overrideTest(); System.out.println(t.a("!1")); }}//错误原因:虽然1.和2.的访问权限控制符和返回值不相等,但是他的参数列表和方法名是相等的,所以这两个方法仍然看做是同一个方法,不满足重载的条件,编译会报错
总结
多态的两种实现方式: override+overload
多态是一种晚绑定,最终的对象引用是在运行期进行确定,编译期还不能确定
虽然多态实现父类的引用指向的是子类的对象,但是真正的调用还是在父类中发生
override的原则:两同两小一大
overload的原则:方法名必须相同,参数列表必须不同,其余两个可以相同,也可以不同
阅读全文
0 0
- java的override和overload详解
- Java面试03--Overload和Override的区别详解
- Overload和Override详解
- overload和override的区别详解
- Java中Overload和Override的区别
- java 多态性 Overload和Override的区别
- Java中Overload和Override的区别
- Java中Overload和Override的区别
- Java中Override和Overload的区别
- Java中overload和override的区别
- Java中overload和override的区别
- java多态性Overload和Override的区别
- Java中Overload和Override的区别
- Java学习--overload和override的区别
- java多态性Overload和Override的区别
- java多态性override和overload的区别
- java中Override 和 Overload的区别
- java多态性Overload和Override的区别
- vue 组件 之 注册 及 组件内data的使用
- 大家好,给大家介绍一下,这是AI
- 最富有的软件工程师
- typedef void (*Fun) () 的理解——函数指针
- 从url中下载文件
- java的override和overload详解
- hdu2955
- Android性能优化之减少过度绘制
- 时钟指针重合问题java实现
- DateUtil工具类
- DateUtil工具类2
- 面试题 编写一个程序,将e:\project\java目录下的所有.java文件复制到 e:\project\jad目录下,并将原来文件的扩展名从.java改为.jad。
- JDBC工具类
- TFT彩屏常见汉字取模方式及相关驱动函数