<返回更多

为什么Java类不支持多继承而接口可以?

2020-09-22    
加入收藏

每个用JAVA的人都知道java不支持多继承,但为什么呢?无论从抽象还是多态等层面思考,感觉都是行得通的,那么为什么不支持呢?

为什么Java类不支持多继承而接口可以?

 

很多人都是分析一旦一个类继承了多个父类,那么父类中如果有相同的成员变量和方法,就不好处理,如下图,这就是Diamond问题

      GrandParent f()
       /           /       Parent1 f()     Parent2 f()
             /            /         Son f()

那么此时子类如果我们只引用 f(),编译器将无法决定它应该调用哪个 f()方法,但此说明不足以让人信服,比如可以强制要求子类必须覆写f()方法。

Java之父,James Gosling在1995年的一份白皮书中给出了关于为什么不支持多继承

JAVA omits many rarely used, poorly understood, confusing features of C++ that in our experience bring more grief than benefit. This primarily consists of operator overloading (although it does have method overloading), multiple inheritance, and extensive automatic coercions.

主要就是说,Gosling认为,多继承是一种很少使用,并且很容易混淆的特性,所以Java语言就像删除操作符重载特性一样删除了多继承这种特性。

也就是说java为了便于程序员理解和使用,去除了一些不容易理解的特性,例如类的多继承。并非不能实现。

那为什么接口可以呢?

针对于Diamond(钻石)问题,接口由于本身都是抽象方法,继承谁都无所谓,都是需要其实现类去实现的,故不存在此问题。

此时有人问了,jdk1.8以后,java接口被赋予了一个新的功能,可以通过default关键字定义非抽象方法,那如果出现一个接口继承的父接口有相同的非抽象方法怎么办呢?

下面我们看看jdk1.8中如何处理

public interface Aservice {
    void say();
    default void bye(){
        System.out.println("a service say bye");
    }}public interface Bservice {
    void say();
    default void bye(){
        System.out.println("b service say bye");
    }}

此时我们定义接口去继承,如下图,发现被强制要求覆写相同的非抽象方法,以保证编译器知道具体执行哪个方法。

为什么Java类不支持多继承而接口可以?

 

因此接口是可以的多继承的,即使jdk1.8中添加了非抽象方法。

声明:本站部分内容来自互联网,如有版权侵犯或其他问题请与我们联系,我们将立即删除或处理。
▍相关推荐
更多资讯 >>>