Java基础之:重写与重载
文章目录
前言
本文只是对我自己学习过程中遇到的疑惑解决后的一个总结,见解看法或许有误,或许片面,仅供参考!欢迎指正!(qq:2530318393 或 评论)
重写是发生在继承(父子类中);重载只发生在一个类中
一、重写的两同两小一大原则
两同:
方法名相同、参数列表相同
两小:
派生类的返回值类型小于或等于超类(当返回值类型是基本数据类型以及void时,必须相同,当是引用类型时必 须小于或等于)、派生类抛出的异常必须小于等于父类
一大:
派生类的方法的访问权限(不明白的可以百度下“Java访问修饰符”)必须大于或等于超类。(补充一小点:父类的privat修饰的方法不能被子类重写!)
二、为什么要有重写?
1.代码的复用性(代码冗余度)
为什么要有重写呢?我在在这之前就有这样的想法:既然重写是对父类提供的方法不满意,才需要进行自己来重写覆盖,那么我为啥还要重写呢?我自己根据我自己的要求来自己单独写一个方法不就行了吗?整这些重不重写的干嘛?但是这种想法毕竟只是一个疑惑,疑惑一般都是一时的。当父类的被重写方法与自己要重写之后的方法所实现的功能几乎完全不同时,感觉的确没啥用,但那只是感觉,其实这样的运用主要体现在多态的运用上,这里就不详说了。还有就是在有一部分功能是相同,或者大部分功能是相同的时候,就很明显了,因为此时我们只需要将不同的部分在子类中进行扩展重写,再加上一句:super.重写的方法名; 就能将实现某部分功能的一堆代码引进来,不需要自己再写一遍了。
这样一看,重写也好像真是有着提高代码的复用性的作用,也就是降低代码冗余度。换个说法:老爸的房子你完全不满意,自己完全重新制造一个,有一半满意,就把不满意的那一半拆了,造上自己满意的,都满意,但是还觉得小了,那就在原来的基础上继续造。这样一想,在某些方面还是有很大的便利的。
见如下举例代码块:
class Animal{
void show(){
System.out.println("我是动物类。");
}
}
class Mammals extends Animal{
//@Override //虽然注释掉了,但是也是重写了
void show(){
super.show(); //沿用父类的
System.out.println("我分属哺乳动物一类!"); //扩展,最终达到自己想要的
}
}
2.不加@override算不算重写?
答案是算的!@Override这是重写的注解,加注解是为了让Java虚拟机能读懂,就算没加,虚拟机也会自己补上。加了注解就等于是告诉编译器这是一个重写方法,所以编译器在检查语法的时候回去查看父类有没有同样的方法,没有的话就会语法报错,有的话就没有任何的问题。
见下面代码块:
class A{
void show(){
System.out.println("我是父类的show方法");
}
}
class B extends A{
//@Override //取消此处的代码注释后,再将父类show()方法注释掉或者删掉就会报错
void show(){
System.out.println("我是子类的show方法");
}
}
三、重载
1.规则:
发生在同一个类中、方法名相同、参数列表不同(参数个数不同;类型不同;多个不同类型参数时,参数排列顺序可以不同;多个相同类型参数时,不能论顺序如何,个数相同都会报错。)。与返回值类型无关,并且与形参变量名无关,例如 void a (int m ,int n){}与void a (int mm ,int nn){}等价,会发生编译报错。
2.作用:
功能的强大化,就像Java的控制台输出方法一样,只要符合参数规则,不论什么类型的都能打印输出到控制台。
3.特殊的一种情况:
当两个类有继承关系时,父类的某个方法在子类中也出现,但是参数列表改变了(符合重载的规则),这里也发生重载了。虽然明面上处于两个类,但是继承使得子类也拥有了父类的,所以相当于子类有了两个方法,并且这两个方法满足重载的规则,所以发生了重载。
例如以下代码块中的show()方法:
class A{
void show(){
System.out.println("我是父类的show方法");
}
}
class B extends A{
void show(int i){
System.out.println("我是子类的show方法");
}
}
总结
重载与重写的区别:
重载:1、Overload为重载
2、发生在一个类中,方法名相同,参数列表不同,方法体不同
3、遵循“编译时绑定”,根据参数列表来绑定,当存在引用变量类型与指向的对象类型不同时,具体根据引用变量的类型来绑定。
重写:1、Override为重写
2、发生在父子类中,方法签名相同(方法名、参数列表),方法体不同
3、遵循“运行时绑定”,根据引用时前面的.引用变量指向的具体类型来确定。