我们知道JDK1.8中增加了接口新特性,不同于之前接口中只能定义抽象方法,更新后在接口中增加了default和static关键字修饰的方法,增加可维护性。
//接口A中定义了新增的default方法和静态方法
public interface A {
abstract public void shout();
default void eat(){
System.out.println("A is eating!");
}
public static void walk(){
System.out.println("A is walking!");
}
}
//接口A中定义了新增的default方法和静态方法
public interface B {
abstract void shout();
default void eat(){
System.out.println("B is eating!");
}
public static void walk(){
System.out.println("B is walking!");
}
}
// test 类实现接口A
public class Test implements A{
@Override
public void shout() {
System.out.println("Test is shouting! ");
}
public static void main(String[] args) {
Test test = new Test();
test.shout();
test.eat();
A.walk();
}
}
注意:
在实现类中只需要重写抽象方法,default和静态方法可以都不用实现,默认使用接口中的方法。
使用default方法可以直接通过Test对象(Test.eat),但是静态方法只能:接口.方法名(A.walk)
疑问1:为什么要在接口中加入非抽象方法?
如果接口中只能定义抽象方法,我们后续要修改接口中内容会对实现类的影响太大了,所有实现类都会受到影响。现在在接口中加入了非抽象方法,对实现类没有影响,想调用就去调用即可。
疑问2:实现类可以像类继承那样调用default方法吗?
为了减少代码,提高复用性,在类继承中会经常直接调用父类方法。
而在接口实现中不能直接调用,因为接口中没有构造器,但是通过这种方法可以:
public class Test implements A{
@Override
public void shout() {
System.out.println("Test is shouting! ");
}
public void play(){
//直接使用接口A中的方法
A.eat();//不可以
A.super.eat();//可以
}
public static void main(String[] args) {
Test test = new Test();
test.shout();
test.eat();
A.walk();
}
}
虽然接口中没有构造器不能调用自己的default方法:不论在接口中还是实现类中
但是有一点我们清楚,那就是实现类可以使用接口中的所有default方法,因此我们可以换个思路:通过实现类调用接口方法:
即:A.super.eat();
疑问3:接口中的default方法如何避免多实现时方法名冲突?
我们知道Java中类只能单继承,原因是如果继承的两个父类中有方法名相同的方法,就导致编译器不知道该以哪个方法为准。
但是在接口中可以实现多实现,是因为在JDK1.8之前的接口中都是抽象方法,没有方法体,既然没有方法体,即使实现多个接口有相同的方法名也不存在冲突,反正都要重写。
那么在JDK1.8中包含了default和静态方法,那么是如何避免方法名冲突?
如果Test类实现接口A和B,但是编译器就会报错,提示还要实现接口中的其他方法。这时,A、B中冲突的方法名就变成了“抽象方法”–>必须要重写/“实现”。
// Test实现类 实现接口A、B,且接口A、B中存在冲突方法 eat()
public class Test implements A,B{
@Override
public void shout() {
System.out.println("Test is shouting! ");
}
@Override
public void eat() {
System.out.println("A、B接口中default冲突方法重写咯!");
}
public static void main(String[] args) {
Test test = new Test();
test.shout();
test.eat();
A.walk();
}
}
*************输出结果***************
Test is shouting!
A、B接口中default冲突方法重写咯!
A is walking!
Process finished with exit code 0