2011-08-28 83 views
0

如何從Super :: Super()調用Super :: printThree?
在下面的例子中,我改用Test :: printThree。基礎構造函數的Java調用庫方法

class Super { 
     Super() { 
     printThree(); // I want Super::printThree here! 
     } 
     void printThree() { System.out.println("three"); } 
} 
class Test extends Super { 
     int three = 3 
     public static void main(String[] args) { 
       Test t = new Test(); 
       t.printThree(); 
     } 
     void printThree() { System.out.println(three); } 
} 

output: 
0 //Test::printThree from Super::Super() 
3 //Test::printThree from t.printThree() 

回答

11

你不能 - 它是一個在子類中被覆蓋的方法;您不能強制進行非虛擬方法調用。如果你想非虛擬地調用一個方法,可以使該方法是私有的或最終的。

一般來說,在一個構造函數中調用一個非final方法是一個壞主意,正是由於這個原因 - 子類構造函數體將不會被執行,所以你在一個環境中有效地調用一個方法,沒有完全初始化。

1

您違反了動態分配和繼承背後的整個想法。不要這樣做(並且很難在java中繞過)。取而代之的是使該功能是私有的和/或最終的,以使其不能被覆蓋在繼承的類中

1

如果Super需要確保printThree()未被覆蓋,則該方法需要被聲明爲final。另外,在Test壓倒一切的方法可以決定調用覆蓋方法,如果選擇:

@Override 
void printThree() { super.printThree(); } 

如果基類沒有標記方法final,它放棄權利,不具有派生類重寫它並按他們的意願去做。

+0

除了他不想在繼承類中調用超級方法,而是相反。所以'super'的想法顯然不會奏效,因爲他的Super類的super是Object。 – Voo

+0

@Voo - 同意了,我只是指出了可能的情況。他想要的是不可能的。 –