為什么Java中不支持多重繼承?
我發(fā)現(xiàn)這個 Java 核心問題很難回答,因?yàn)槟愕拇鸢缚赡懿粫屆嬖嚬贊M意,在大多數(shù)情況下,面試官正在尋找答案中的關(guān)鍵點(diǎn),如果你提到這些關(guān)鍵點(diǎn),面試官會很高興。在 Java 中回答這種棘手問題的關(guān)鍵是準(zhǔn)備好相關(guān)主題, 以應(yīng)對后續(xù)的各種可能的問題。
這是非常經(jīng)典的問題,與為什么 String 在 Java 中是不可變的很類似; 這兩個問題之間的相似之處在于它們主要是由 Java 創(chuàng)作者的設(shè)計(jì)決策使然。
為什么Java不支持多重繼承, 可以考慮以下兩點(diǎn):
1)第一個原因是圍繞鉆石??形繼承問題產(chǎn)生的歧義,考慮一個類 A 有 foo() 方法, 然后 B 和 C 派生自 A, 并且有自己的 foo() 實(shí)現(xiàn),現(xiàn)在 D 類使用多個繼承派生自 B 和C,如果我們只引用 foo(), 編譯器將無法決定它應(yīng)該調(diào)用哪個 foo()。這也稱為 Diamond 問題,因?yàn)檫@個繼承方案的結(jié)構(gòu)類似于菱形即使我們刪除鉆石的頂部 A 類并允許多重繼承,我們也將看到這個問題含糊性的一面。如果你把這個理由告訴面試官,他會問為什么 C++ 可以支持多重繼承而 Java不行。嗯,在這種情況下,我會試著向他解釋我下面給出的第二個原因,它不是因?yàn)榧夹g(shù)難度, 而是更多的可維護(hù)和更清晰的設(shè)計(jì)是驅(qū)動因素, 雖然這只能由 Java 言語設(shè)計(jì)師確認(rèn),我們只是推測。維基百科鏈接有一些很好的解釋,說明在使用多重繼承時,由于鉆石問題,不同的語言地址問題是如何產(chǎn)生的。
2)對我來說第二個也是更有說服力的理由是,多重繼承確實(shí)使設(shè)計(jì)復(fù)雜化并在轉(zhuǎn)換、構(gòu)造函數(shù)鏈接等過程中產(chǎn)生問題。假設(shè)你需要多重繼承的情況并不多,簡單起見,明智的決定是省略它。此外,Java 可以通過使用接口支持單繼承來避免這種歧義。由于接口只有方法聲明而且沒有提供任何實(shí)現(xiàn),因此只有一個特定方法的實(shí)現(xiàn),因此不會有任何歧義。