多態の実現メカニズムは何ですか.
8664 ワード
文書ディレクトリメソッドは をカバーするよくある筆記試験問題 マルチステートは、オブジェクト向けプログラム設計におけるコード再利用の重要なメカニズムであり、同じ操作が異なるオブジェクトにある場合、異なる意味があり、例えば、同じ「+」操作を実行し、「3+4」は正数加算を実現し、「3」+「4」は文字列の接続を実現する.Java言語では、マルチステートには主に以下の2つの表現があります.
1)メソッドのリロード.リロードとは、同じクラスに複数の同名のメソッドがあることを意味しますが、これらのメソッドには異なるパラメータがあるため、コンパイル時にどのメソッドが呼び出され、コンパイル時にマルチステートであるかを決定できます.リロードはクラス内のメソッド多様性と見なすことができる.
2)メソッドの上書き.子クラスは親クラスのメソッドを上書きできるため、同じメソッドは親クラスと子クラスで異なる表現形式を持つことになります.Java言語では、ベースクラスの参照変数は、ベースクラスのインスタンスオブジェクトだけでなく、そのサブクラスのインスタンスオブジェクトも指すことができます.同様に、インタフェースの参照変数は、実装されたインスタンスオブジェクトを指すこともできます.プログラム呼び出しの実行方法は、実行中に動的にバインドされます(バインドとは、メソッド呼び出しとメソッドボディを接続することです).変数が指す特定のインスタンスオブジェクトを参照する方法です.この動的バインド法により多状態を実現した.どのメソッドが呼び出されるかは、実行時にのみ決定されるため、メソッドオーバーライドによって実現されるマルチステートは、実行時マルチステートとも呼ばれ、以下のように例示される.
メソッドオーバーライド
プログラムの実行結果は次のとおりです.
上記の例では、子クラスDerivedのf()メソッドとg()メソッドは親クラスBaseのメソッドと同名であるため、DeriveredのメソッドはBaseのメソッドを上書きする.Base b=new Deriver()文を実行すると、Baseクラスのコンストラクション関数が呼び出されますが、Baseのコンストラクション関数では、Java言語のマルチステート特性のため、親Baseのg()メソッドではなく、サブクラスDerivedのg()メソッドが呼び出されますので、Deriver g()が出力されます.実際にDeriverクラスのオブジェクトが作成されているため、後のメソッド呼び出しではサブクラスのDeriverメソッドが呼び出されます.また、クラス内のメソッドのみがマルチステートの概念を持ち、クラス内のメンバー変数にはマルチステートの概念はありません.例は次のとおりです.
私たちの運行結果は
このように、メンバー変数はマルチステートを実装できません.メンバー変数の値が親クラスであるかサブクラスであるかは、作成オブジェクトのタイプに依存せず、定義された変数のタイプに依存します.これは、コンパイル中に決定されます.上記の例では、bが属するタイプがBaseであるため、b.iはBaseクラスで定義されたiを指す.したがって、プログラム出力結果は1である.
よくある筆記試験問題
JAvaでは、マルチステート用のメカニズムを2つ提供していますか?答え:コンパイル時マルチステートと実行時マルチステート.コンパイル時マルチステートはメソッドのリロードによって実現され、実行時マルチステートはメソッドのオーバーライド(サブクラスオーバーライド親メソッド)によって実現されます.
1)メソッドのリロード.リロードとは、同じクラスに複数の同名のメソッドがあることを意味しますが、これらのメソッドには異なるパラメータがあるため、コンパイル時にどのメソッドが呼び出され、コンパイル時にマルチステートであるかを決定できます.リロードはクラス内のメソッド多様性と見なすことができる.
2)メソッドの上書き.子クラスは親クラスのメソッドを上書きできるため、同じメソッドは親クラスと子クラスで異なる表現形式を持つことになります.Java言語では、ベースクラスの参照変数は、ベースクラスのインスタンスオブジェクトだけでなく、そのサブクラスのインスタンスオブジェクトも指すことができます.同様に、インタフェースの参照変数は、実装されたインスタンスオブジェクトを指すこともできます.プログラム呼び出しの実行方法は、実行中に動的にバインドされます(バインドとは、メソッド呼び出しとメソッドボディを接続することです).変数が指す特定のインスタンスオブジェクトを参照する方法です.この動的バインド法により多状態を実現した.どのメソッドが呼び出されるかは、実行時にのみ決定されるため、メソッドオーバーライドによって実現されるマルチステートは、実行時マルチステートとも呼ばれ、以下のように例示される.
メソッドオーバーライド
class Base{
public Base(){
g();
}
public void f(){
System.out.println("Base f()");
}
public void g(){
System.out.println("Base g()");
}
}
class Derived extends Base{
public void f(){
System.out.println("Derived f()");
}
public void g(){
System.out.println("Derived g()");
}
}
public class Test {
public static void main(String[] args) {
Base b=new Derived();
b.f();
b.g();
}
}
プログラムの実行結果は次のとおりです.
Derived g()
Derived f()
Derived g()
上記の例では、子クラスDerivedのf()メソッドとg()メソッドは親クラスBaseのメソッドと同名であるため、DeriveredのメソッドはBaseのメソッドを上書きする.Base b=new Deriver()文を実行すると、Baseクラスのコンストラクション関数が呼び出されますが、Baseのコンストラクション関数では、Java言語のマルチステート特性のため、親Baseのg()メソッドではなく、サブクラスDerivedのg()メソッドが呼び出されますので、Deriver g()が出力されます.実際にDeriverクラスのオブジェクトが作成されているため、後のメソッド呼び出しではサブクラスのDeriverメソッドが呼び出されます.また、クラス内のメソッドのみがマルチステートの概念を持ち、クラス内のメンバー変数にはマルチステートの概念はありません.例は次のとおりです.
class Base1{
public int i=1;
}
class Deriver1 extends Base1{
public int i=2;
}
public class Test1 {
public static void main(String[] args) {
Base1 b = new Deriver1();
System.out.println(b.i);
}
}
私たちの運行結果は
1
このように、メンバー変数はマルチステートを実装できません.メンバー変数の値が親クラスであるかサブクラスであるかは、作成オブジェクトのタイプに依存せず、定義された変数のタイプに依存します.これは、コンパイル中に決定されます.上記の例では、bが属するタイプがBaseであるため、b.iはBaseクラスで定義されたiを指す.したがって、プログラム出力結果は1である.
よくある筆記試験問題
JAvaでは、マルチステート用のメカニズムを2つ提供していますか?答え:コンパイル時マルチステートと実行時マルチステート.コンパイル時マルチステートはメソッドのリロードによって実現され、実行時マルチステートはメソッドのオーバーライド(サブクラスオーバーライド親メソッド)によって実現されます.