Java小白踩坑錄 - Java中繼承隱藏覆寫

繼承 Inheritance / 隱藏 hide / 覆寫 override

Java 中有繼承 Inheritance/隱藏 hide/覆寫 override 的概念,我們暫且不管他們的區別,先看看最近發生的一件小事,Boss 在開會時說錯了一個數字,Leader 趕緊說:”那是我弄錯的“,程序猿想找到 Boss 說的數字時,卻怎麼也不行,這是怎麼回事呢?請看案情回放:

public class Conference {
    public static void main(String[] args) {
        System.out.println(new Leader().sales);
    }
}
class Boss {
    public Integer sales=10000;
}
class Leader extends Boss{
    private Integer sales=9000;
}

咋一看,會打印 Leader 的銷售量數據 9000,但仔細分析來看,Leader 類的 sales 變量是私有的,程序不能編譯通過。該程序確實不能編譯,但是錯誤出在 Conference 類中。原因:在 Conference 中調用的是 new Leader() 即 leader 的實例,不是 Leader 類,一個覆寫方法的訪問修飾符,所提供的訪問權限與被覆寫方法的訪問修飾符所提供的訪問權限相比,至少要一樣多[JLS 8.4.8.3]。

因爲 sales 是一個域,所以 Leader.sales 隱藏(hide)了 Boss.sales,而不是覆蓋了它 [JLS 8.3]。對一個域來說,當它要隱藏另一個域時,如果隱藏域的訪問修飾符提供的訪問權限比被隱藏域的少,儘管這麼做不可取的,但是它確實是合法的。

其實我們還是可以找到老闆的所說的 sales 的。如下:

public class Conference {
    public static void main(String[] args) {
        System.out.println(((Boss)new Leader()).sales);
    }
}
class Boss {
    public Integer sales=10000;
}
class Leader extends Boss{
    private Integer sales=9000;
}

總結

覆寫與隱藏之間的一個非常大的區別。一旦一個方法在子類中被覆寫,你就不能在子類的實例上調用它了(除了在子類內部,通過使用 super 關鍵字來方法)。然而,你可以通過將子類實例轉型爲某個超類類型來訪問到被隱藏的域,在這個超類中該域未被隱藏。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章