最近、親クラスのオブジェクトにサブクラスのオブジェクトを割り当てる経験があるので、それを共有したいと思います。しかし、私のレベルには限界があるので、修正と批判をお願いします。
身近なところでは、いくつかの小さな例を紹介しますので、ご覧ください。
テスト 1
親クラス:
サブクラス:
結果: これは親クラスの print() メソッドです - この時点のオブジェクトは Subclass@126b249 です
この時点でのオブジェクトは Subclass@126b249 です。
例証します:
サブクラス sup=new サブクラス();
宣言されたオブジェクトは親クラス オブジェクトですが、実際のメモリ空間はサブクラス オブジェクトに属します。
親クラスから継承したメソッド public void print() が呼び出され、サブクラス オブジェクトの名前解決が出力されます。
結論: コンパイル時に宣言されたオブジェクトは親クラスのオブジェクトですが、実行時にはサブクラスのオブジェクトになります。サブクラスが親クラスのメソッドをオーバーライドしない場合、この時点のオブジェクトは親クラスから継承したメソッドを呼び出します。
テスト2
親クラス:
サブクラス:
結果: これはサブクラスの print() メソッドです - この時点でのオブジェクトは Subclass@126b249 です
この時点でのオブジェクトは Subclass@126b249 です。
例証します:
前の例に基づいて、親クラスの print() メソッドを書き直しました。このとき、サブクラスの print() メソッドが呼び出されます。
結論: 前の例の結論に基づいて、この時点で、サブクラスが親クラスのメソッドを記述していない場合、そのオブジェクトは確かにサブクラス オブジェクトであるという結論に達しました。
次に、この時点のオブジェクトは親クラスから継承したメソッドを呼び出します。それ以外の場合、オブジェクトはこの時点でサブクラスのメソッドを呼び出します。
質問: 上記のテストから次の結論を導き出すことはできますか: サブクラス オブジェクトを親クラス オブジェクトに割り当てます (つまり、Supclass sup=new Subclass())。
取得するのはサブクラス オブジェクトです。つまり、sup はサブクラス オブジェクトです。
テスト 3
親クラス:
サブクラス:
結果: この時点の属性: 親クラスの属性
注: 最初のテストに基づいて、属性 className を親クラスに追加し、サブクラスでこの属性をオーバーライドしました。
ただし、このときオブジェクトのプロパティを出力すると、親クラスのプロパティになります。
結論: サブクラス オブジェクトを親クラス オブジェクトに割り当てる場合、メソッドとプロパティは通常の継承関係とは大きく異なります。
質問:
このときのオブジェクトはサブクラスのオブジェクトでしょうか、それとも親クラスのオブジェクトでしょうか?
推測を始めます:
推測する前に、いくつか確認しておく必要がある点があります。
1. 新しいサブクラス オブジェクトを作成すると、親クラス オブジェクトのコンストラクターも同時に実行されます。つまり、親クラスとサブクラス オブジェクトのいくつかの必要な情報が同じメモリ空間を占有します。
メソッドをオーバーライドすると、スーパー オブジェクトを使用して親クラスを参照できます。
2. Java のオブジェクトは完全なオブジェクト指向ではありません。つまり、オブジェクトの属性とメソッドが同時にオブジェクトにカプセル化されません。
ただし、オブジェクトには独自の属性がありますが、メソッドはクラス内のメソッドを参照します。これは、クラス内の属性とメソッドの参照をオブジェクトにカプセル化していると言えます。
したがって、オブジェクトによって呼び出されるメソッドはそれ自体のメソッドではなく、クラス内のメソッドです。なぜJavaがこれを行うのかはわかりません。
3. オブジェクトがメモリにロードされるとき、最初にクラスがメモリにロードされ、その後クラスがメモリに残るはずです。クラスがいつメモリから消えるかについてはわかりません。
オブジェクトをリサイクルするのと同じように、Java には独自のリサイクル メカニズムが必要だと思います。
4. コンパイルと実行はまったく別のことです。コンパイル中に行う主な作業は、オブジェクトの型の宣言、属性の割り当て、構文エラーのチェックなどです。
ランタイムが行うことは、オブジェクトをメモリにロードし (通常は new を使用し、リフレクションもよく使用されます)、コード実行関数を実行することなどです。
5. あなた、読者、そして私がこれらの点で互いに共鳴しない場合、またはこれらの点について同じ理解を持っていない場合、あなたは私がナンセンスなことを言っていると思うでしょう。
もしかしたら、私のエキスパートスコアが低すぎるため、私の信憑性が低いと思われるかもしれませんが、私が言いたいのは、学習に順序はなく、最初にマスターした人が先だということです。
はは、エキスパート ポイントをマイナスの値に変える準備はできています。これ以上ナンセンスではありません。続けましょう。
投機:
1. Supclass sup=new Subclass() をコンパイルすると、sup オブジェクトは Supclass クラスとして宣言されるため、sup オブジェクトの属性は親クラス オブジェクトの属性の値になります。
3. 手順 2 に引き続き、親クラスのメソッドをオーバーライドすると、sup オブジェクトのメモリ空間はサブクラス オブジェクトのメモリ空間であるため、サブクラスのメソッド public void print() がメモリにロードされます。
したがって、呼び出すのはサブクラスのメソッド public void print() です。親クラスのオーバーライドされたメソッドを呼び出す必要がある場合は、super を使用する必要があります。
この一節でテスト 2 について説明できます。
要約:
以下は完全に個人的な意見です。
サブクラス オブジェクトを親クラス オブジェクトに割り当てると、結果のオブジェクトは次のようなオブジェクトになります。
親クラスのオブジェクトとしてコンパイルされますが、サブクラスのオブジェクトとして実行されます。具体的な特徴は次のとおりです。
1. 親クラスのオブジェクトとして宣言されている 2. 親クラスの属性がある 3. サブクラスのメモリ空間を占有する 4. サブクラスのメソッドが親クラスのメソッドをオーバーライドする場合、その時点でオブジェクトはサブクラスのメソッドを呼び出します。それ以外の場合は、自動的に継承が行われます。親クラスのメソッドと呼ばれます。
5. そのメソッドを使用するとき、このオブジェクトは親クラス オブジェクトでもサブクラス オブジェクトでもないと思います。
それをサブクラス オブジェクトとして扱いますが、そのプロパティを使用する場合は親クラス オブジェクトとして扱います。
親クラスの属性を占有し、サブクラスのメソッドを利用するオブジェクトですが、どのようなオブジェクトなのかは宣言次第だと思いますが、親クラスのオブジェクトとみなすべきですが、サブクラスを持っています。メソッド。
考えてみてください:
テスト 3 に基づいて、サブクラスの属性を抽出するにはどうすればよいでしょうか? ? ? ? ?