2016-08-23 70 views
1

爲什麼doAction(A a)會在這種情況下被選中?這是如何調用java中繼承的方法解決的?

您能否根據參數類型建議一些關於方法選擇的文章?

class A { } 
class B extends A { } 
class D { 
    void start(A a){ 
     doAction(a); 
    } 
    void doAction(A a) { 
     System.out.println("A action"); 
    } 
    void doAction(B b) { 
     System.out.println("B action"); 
    } 
} 
public class Test { 
    public static void main(String[] args) { 
     new D().start(new B()); 
    } 
} 
+0

我不確定它是否真的重複,因爲它不會詢問如何根據執行時類型進行選擇。答案仍然相關,但... –

回答

4

爲什麼doAction(A)將在這種情況下可以選擇?

因爲這是唯一適用的方法。基於編譯時間參數的類型,在編譯時間執行過載分辨率。

doAction(B)方法是不適用的,因爲有一個從A的隱式轉換(你們的論據類型)B(參數的類型)。您可以在值轉換爲B這樣的:

doAction((B) a); 

在這一點上兩種方法將適用,但重載決議會選擇doAction(B b)爲更具體doAction(A a)。當然,如果您將不是的引用傳遞給B的實例,它也會失敗。

您應該閱讀JLS 15.12.2以瞭解重載分辨率的精確細節。