Java 8 默认方法继承 [英] Java 8 default method inheritance

查看:23
本文介绍了Java 8 默认方法继承的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

假设有以下类型:

public interface Base {默认无效 sayHi(){System.out.println("你好来自基地");}}公共接口 Foo 扩展了 Base {@覆盖默认无效 sayHi(){System.out.println("hi from foo");}}公共接口 Bar 扩展 Base {}公共类 MyClass 实现 Foo, Bar {公共静态无效主(字符串 [] args){MyClass c = new MyClass();c.sayHi();}}

在这种情况下,如果执行 main,则会打印hi from foo".为什么 Foo 的实现优先?Bar 不从 Base 继承 sayHi(),因为如果 MyClass 只实现 BarBase 实现会被调用吗?所以代码仍然无法编译是有意义的.另外,既然 Bar 应该有 BasesayHi() 实现,为什么我不能在 MyClass喜欢:

@Override公共无效 sayHi() {Bar.super.sayHi();}

尝试这样做时出现以下错误:

<块引用>

默认超级调用方法中的错误类型限定符 Bar,在 Foo 中覆盖了 sayHi()

解决方案

此行为是使用您在 JLS 9.4.1,只是更改了一些名称:

interface Top {默认字符串名称(){ 返回未命名";}}接口左扩展顶部{默认字符串名称() { return getClass().getName();}}接口 Right 扩展 Top {}接口底部延伸左,右{}

<块引用>

Right 从 Top 继承 name(),Bottom 从 Left 继承 name(),不对.这是因为来自 Left 的 name() 覆盖了声明顶部的 name().

JLS 似乎没有给出任何我能看到的特别具体的原因;这就是 Java 设计者决定继承的工作方式.

Let's say there are following types:

public interface Base {

    default void sayHi(){
        System.out.println("hi from base");
    }
}

public interface Foo extends Base {
    @Override
    default void sayHi(){
        System.out.println("hi from foo");
    }
}

public interface Bar extends Base {
}

public class MyClass implements Foo, Bar {
    public static void main(String[] args) {
        MyClass c = new MyClass();
        c.sayHi();
    }
}

In this scenario, if main is executed, "hi from foo" is printed. Why does Foo's implementation take precedence? Doesn't Bar inherit sayHi() from Base, since if MyClass was to only implement Bar, the Base implementation would be called? So it would make sense for the code to still not compile. Also, since Bar should have Base's implementation of sayHi(), why can't I override it in MyClass like:

@Override
public void sayHi() {
    Bar.super.sayHi();
}

The following error occurs when trying to do so:

bad type qualifier Bar in default super call method, sayHi() is overridden in Foo

解决方案

This behavior is specified using almost your exact example in JLS 9.4.1, just with some names changed around:

interface Top {
    default String name() { return "unnamed"; }
}
interface Left extends Top {
    default String name() { return getClass().getName(); }
}
interface Right extends Top {}

interface Bottom extends Left, Right {}

Right inherits name() from Top, but Bottom inherits name() from Left, not Right. This is because name() from Left overrides the declaration of name() in Top.

The JLS doesn't seem to give any especially concrete reason that I can see; this is just how the Java designers decided inheritance would work.

这篇关于Java 8 默认方法继承的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆