簡體   English   中英

涉及內部類時,Java繼承如何工作

[英]How does Java inheritance work when inner classes are involved

當存在內部類時,我很難理解繼承在Java中的工作方式。 我目前正在研究子類需要稍微更改其父類內部類功能的東西。 我在下面提出了一個更簡單,類似的示例。

我希望此代碼可以打印“我是ChildClass.InnerClass”,但可以打印“我是ParentClass.InnerClass”。 為什么是這樣? 另外,如果我將main中的obj對象更改為ChildClass類型,則輸出更改為“我是ChildClass.InnerClass”。 為什么是這樣?

通常,建議的改變對象父類內部對象行為的方法是什么?

class InnerClassTest {
   //-----------------------------------------------------------------------
   // PARENT CLASS
   class ParentClass {
      public ParentClass() {
         x = new InnerClass();
      }

      InnerClass x;

      class InnerClass {
         public void speak() {
            System.out.println("I am a ParentClass.InnerClass");
         }
      }
   }

   //-----------------------------------------------------------------------
   // CHILD CLASS
   class ChildClass extends ParentClass {
      public ChildClass() {
         x = new InnerClass();
      }

      InnerClass x;

      class InnerClass extends ParentClass.InnerClass {
         public void speak() {
            System.out.println("I am a ChildClass.InnerClass");
         }
      }
   }

   //-----------------------------------------------------------------------
   // MAIN
   public static void main(String[] args) {
      ParentClass obj = (new InnerClassTest()).new ChildClass();
      obj.x.speak();
   }
}

變量不像方法那樣“被覆蓋”。

在您的通話中,您希望xChild但這不是因為x是變量,而不是方法。

但請注意:您的引用類型是ParentClass因此obj.x指向ParentClassInnerClass屬性,即使parentClass背后的實際實例是ChildClass

為了顯示您期望的句子,您必須將類型引用更改為ChildClass

public static void main(String[] args) {
      ChildClass obj = (new InnerClassTest()).new ChildClass();
      obj.x.speak();
}

為了更好地理解該概念,請嘗試在ParentClassChildClass類中都定義一個方法:

public InnerClass getInnerClass(){
  return x;
}  

並將x私有。

因此,“替代概念”適用。

在這種情況下,您的最終通話是:

ParentClass obj = (new InnerClassTest()).new ChildClass();
obj.getInnerClass().speak();

要更改內部類的行為,請考慮使用模板方法模式或更好的方法策略模式 (因為更加尊重DIP)

刪除重新聲明

InnerClass x; 

來自兒童班。 因此,您只有一個x並且將在子類的構造函數中重新分配。 表示一個x (指的是在子ctor中創建的對象)。

它在父類中隱藏了一個。 這就是為什么您最終擁有兩個字段,分別引用兩個不同的對象的原因。 由於存在變量的靜態(編譯時或早期)綁定,

ParentClass obj; 
//obj.x means the x in parent

ChildClass obj; 
//obj.x means the x in child

通常,建議的改變對象父類內部對象行為的方法是什么?

我建議一開始就使用較簡單的設計。 子類應該通過覆蓋其方法來修改其父類的行為,因此我只需添加一些工廠方法newInnerClass()即可覆蓋此依賴項的創建,並在類層次結構的頂部管理該對象。

這將比您建議的方法更加靈活,因為newInnerClass()可以實例化定義在任何地方的類,只要它具有正確的接口即可。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM