抽象超类的默认接口方法

L0l*_*pk3 9 java java-8 default-method

可以说我有以下结构:

abstract class A {
     abstract boolean foo();
}

interface B {
     default boolean foo() { return doBlah(); }
}

class C extends A implements B {
    //function foo
}
Run Code Online (Sandbox Code Playgroud)

Java现在会抱怨该类C必须实现抽象方法foo A.通过重新定义函数C并简单地调用,我可以相对容易地解决这个问题B.super.foo();.

但是我不明白为什么接口的默认函数B不能单独满足这个要求,我希望能更好地理解java的底层机制.

Maa*_*nen 6

接口中的默认方法用于防止在向接口添加方法时破坏依赖于接口的程序。

在您描述的情况下,尚不清楚接口中的默认方法(根据设计必须稍后添加)是否真正履行抽象类最初设想的合同。

在这种情况下,Java 抱怨更安全。

以上文字是我对 JLS SE8 规范 9.4.1.3中段落的解释,我引用:

同样,当继承具有匹配签名的抽象方法和默认方法时,我们会产生错误。在这种情况下,可以优先考虑其中之一 - 也许我们会假设默认方法也为抽象方法提供了合理的实现。但这是有风险的,因为除了巧合的名称和签名之外,我们没有理由相信默认方法的行为与抽象方法的约定一致——默认方法在子接口最初开发时甚至可能不存在。在这种情况下,要求用户主动断言默认实现是合适的(通过重写声明)会更安全。


L0l*_*pk3 2

The answer of Jacob G. inspired me to come up with this solution:

interface Z {
     abstract boolean foo();
}

abstract class A implements Z {

}

interface B extends Z {
     default boolean foo() { return doBlah(); }
}

class C extends A implements B {

}
Run Code Online (Sandbox Code Playgroud)

This way all subclasses of class A are required to define a method foo(), Without requiring every class that implements B to re-implement it.