Java默认方法以及方法冲突

默认方法:

  1. 为什么引入默认方法?

  2. 如何使用?

  3. 默认方法带来的问题以及解决方法

1.在定义接口时,我们声明了一系列方法,而方法的实现是通过接口的实现类来完成的,接口的出发点是站在顶层考虑问题,对于一个有着很悠久历史的接口来说,如果它有着很多实现类,当想在接口中增加一个功能,当然对于顶层接口来说so easy,但这对于众多的实现类以及已经将接口应用于实际项目中的人员来说,就有点麻烦了,因为每个实现类都要为新增的方法提供根据自己需求的具体实现,同时如果接口的api已经公示出去,则对于使用者,以及在原来接口上提供了具体实现的厂商来说,要么继续使用旧的接口,不做改动,要么实现新的接口,又因为不同的厂商是根据旧的接口来实现自己的业务,所以对于业务的改动可以说是牵一发而动全身,疼啊。。。

因此,为了解决这个问题,Java8提出了默认方法,同时也允许在接口中声明静态方法。

2.默认方法可以指定接口方法的默认实现,即接口能够提供方法的具体实现,因此,如果实现接口,不显式的提供该方法的具体实现,就会自动继承默认的实现。

默认方法由default修饰符修饰,并像类中声明的其他方法一样包含方法体。

interface AClass{
	default void hello() {
		System.out.println("i \' am A class");
	}
}

3.java没有多继承,但是一个类可以继承多个接口,就相当于实现了多继承的问题,下面我们为了方便,全部用多继承来说明问题,如果一个类继承了多个类,而这写父类中又有相同的函数签名,当子类调用父类中的相同的函数签名时,具体执行哪个方法了???

要解决这个问题,必须遵循以下三个规则:

⑴类中的方法优先级最高,类或者父类中声明的方法的优先级高于任何声明为默认方法的优先级

⑵如果无法依据第一条进行判断,则子接口的优先级更高:函数签名相同的时候,优先选择拥有最具体实现的默认方法的接口,

⑶如果还是无法判断,继承了多个接口的类必须通过显示覆盖和调用期望的方法;

下来用实际例子说明:

interface AClass{
	default void hello() {
		System.out.println("i \' am A class");
	}
}

class BClass implements AClass{
	 public void hello() {
		System.out.println("i \' am B class");
	}
}
class CClass extends BClass implements AClass{
	public static void main(String[] args) {
		new CClass().hello();
	}
}

输出结果为:i ' am B class

解析:根据第二条规则,B实现A接口,C继承B,实现A,应该选择提供更具体实现的默认方法的接口,即B比A更具体,所以输出B的hello()方法;

interface DClass{
	default void hello() {
		System.out.println("i \' am D class");
	}
}
class EClass implements AClass{
	 public void hello() {
			System.out.println("i \' am E class");
		}
}
class FClass extends BClass implements AClass ,DClass{
	public static void main(String[] args) {
		new FClass().hello();
	}
}

输出结果是: i  ' am B class ,原理同上。

class GClass  implements AClass ,DClass{
	public static void main(String[] args) {
		new GClass().hello();
	}
}

根据规则,A,D平行关系,无法判断,则必须显式的覆盖hello方法;

因此,这个类会报错,同时iDE会提示:

菱形继承问题:

interface HClass extends AClass{}
interface IClass extends AClass{}

class JClass implements HClass ,IClass{
	public static void main(String[] args) {
		new JClass().hello();
	}
}

因为只有AClass声明了一个默认方法,所以结果是 A class

如果HClass 也提供了默认的hello方法,则根据规则(2),则会输出 H的hello方法。

 

如有问题,敬请指出,谢谢,本书参考《Java8实战》  ,,由衷感谢此书作者为我们提供学习内容

全部评论

相关推荐

牛客101244697号:这个衣服和发型不去投偶像练习生?
点赞 评论 收藏
分享
11-09 14:54
已编辑
华南农业大学 产品经理
大拿老师:这个简历,连手机号码和照片都没打码,那为什么关键要素求职职位就不写呢? 从上往下看,都没看出自己到底是产品经理的简历,还是电子硬件的简历? 这是一个大问题,当然,更大的问题是实习经历的描述是不对的 不要只是去写实习流程,陈平,怎么去开会?怎么去讨论? 面试问的是你的产品功能点,是怎么设计的?也就是要写项目的亮点,有什么功能?这个功能有什么难处?怎么去解决的? 实习流程大家都一样,没什么优势,也没有提问点,没有提问,你就不得分 另外,你要明确你投的是什么职位,如果投的是产品职位,你的项目经历写的全都是跟产品无关的,那你的简历就没用 你的面试官必然是一个资深的产品经理,他不会去问那些计算机类的编程项目 所以这种四不像的简历,在校招是大忌
点赞 评论 收藏
分享
点赞 评论 收藏
分享
点赞 收藏 评论
分享
牛客网
牛客企业服务