Common Sense
学习Java语言的一开始,就被任何一本教科书告知,Java语言是不支持多重继承的。但是可以利用接口完成多重实现。于是这个“事实”就作为一条常识,神一样的存在了。
Why can not?
当被问及这条神律为啥在Java语言中存在时,很多人就说不清楚了。老外的这篇文章说了大家比较公认的一个问题:“钻石问题”。这里,具体的细节请参考上面原文,下面把原文中的一个关键性说明图例摘抄过来:
看到这个图片,大家应该了解了。
这里,从类的继承体系的最上层A开始,所有子类都有一个foo()方法。当D类没有override他的父类(们)的foo()方法时,如果在程序的运行期,当前的对象引用指向的是D的对象实例,并且调用了他的foo方法,那问题就来了,这个foo()到底使用B的foo()还是C的foo()呢?
说到这里,就涉及到了Java语言本身对多态机制的实现了。
JVM在运行期,在调用方法时,会invoke当前实例的对应的方法。如果当前实例对应类存在这个方法(比如foo),就直接使用当前实例对应类的foo方法,如果当前实例对应类并不存在这个方法,则按照继承关系,从下往上对父类进行搜索。直到找到为止,并进行调用。
说到这里,我们似乎可以得出结论:Java确实不应该支持多重继承!
Why other language can work around the problem?
如果想想像C++这种面向对象的语言,同样也存在这个问题,但是C++本身却没有排斥多重继承的机制,而且直接在语言层面提供了支持。所以,可想而知,多重继承本身并不是技术上不可解决的问题。但排除了上面所说的“钻石问题”的因素之外,还有啥其他的原因让Java不支持多重继承呢?
上面的那篇老外文章中也提到了一个原因是要简化设计。这点理解起来并没有那么好懂,至少目前我自己理解的并不透彻。。。