Java の改善 (パート 2) - Java の 3 つの主要な特性の継承を理解する

黄舟
リリース: 2017-02-09 13:30:49
オリジナル
991 人が閲覧しました

「Think in Java」には次のような言葉があります。コードの再利用は、Java の多くの目を引く機能の 1 つです。しかし、言語が非常に革新的であるためには、コードをコピーして変更できるだけでは十分ではなく、さらに多くのことができる必要があります。この文の中で最も目を引くのは、私たちプログラマーが追求してきた「コードを最大限に再利用する」ということです。次に、Java の 3 つの大きな特徴の 1 つである、コードを再利用する方法を紹介します。 1つ――相続。解 継承

説明する前に、まず例を読みます。この例は、以前のブログ投稿 (Java の改良記事 ----- Java の 3 つの主要な機能を理解する) です。

Java の改善 (パート 2) - Java の 3 つの主要な特性の継承を理解する ここから、妻と夫のクラスはそれぞれの夫と妻を除いてすべて同じであることがわかります。コードの再利用を最大限にしたい人として、別の愛人がいる場合、そのようなコードの繰り返しは許容できません。愛人、愛人、愛人…(言い過ぎです)、こう書かないといけないのでしょうか?では、これらのクラスの再利用性を実現するにはどうすればよいでしょうか?相続を活用しよう! !まず第一に、ソフトウェア プログラミングの世界から離れましょう。常識的に考えて、夫、妻、第 3 位、第 4 位はすべて人間であり、名前、年齢、性別など、何らかの共通点があることがわかります。ここから、彼らはすべて人間の属性と行動を持ち、またこれらの属性と行動を人間から受け継いでいることがわかります。

上記のことから、継承の概念は、既存のクラスの定義を基礎として使用して、新しいクラスの定義、または新しい関数を追加するテクノロジーであることがわかります。親クラスの関数を使用できますが、親クラスから選択的に継承することはできません。継承を使用すると、以前のコードを再利用できるため、開発効率が大幅に向上します。

妻と夫の継承を使用すると、コードの量が削減されるだけでなく、それらの関係も明確に確認できます。

Java の改善 (パート 2) - Java の 3 つの主要な特性の継承を理解する 継承は「is-a」関係を記述するもので、2 つのオブジェクト A と B がある場合、「A は B である」と記述できれば、A が B を継承することを意味し、B は親クラスまたはと呼ばれる継承者になります。スーパークラス、A はサブクラスまたは派生クラスと呼ばれる後継クラスです。是 実は、相続には相続の専門化だけでなく、相続特有の特徴もあります。例えば、猫はネズミを捕まえたり、木に登ったりするなど、他の動物にはない特徴を持っています。同時に、相続関係では、相続人が相続人を完全に置き換えることはできますが、その逆はできません。たとえば、猫は動物であると言えますが、実際にはその動物は猫であるとは言えません。これを「上向きの変革」と呼ぶ理由」については、以下で紹介します。

確かに、継承はクラスがどのように相互に関係し、特性を共有するかを定義します。いくつかの同一のクラスまたはよく知られたクラスについては、それらの共通の動作や属性を抽象化し、それらを親クラスまたはスーパークラスとして定義し、これらのクラスを使用して親クラスを継承することができます。これらのクラスは、親クラスのプロパティやメソッドを持つだけではありません。独自の一意のプロパティやメソッドを定義することもできます。継承を同時に使用する場合は、次の 3 つの文を覚えておいてください:

1. サブクラスは、非 Private の親クラスの属性とメソッドを持ちます。

2. サブクラスは独自の属性とメソッドを持つことができます。つまり、サブクラスは親クラスを拡張できます。

3. サブクラスは、独自の方法で親クラスのメソッドを実装できます。 (後で紹介します)。

要約すると、継承を使用すると、すべてのサブクラスの共通属性を親クラスに入れてコードの共有を実現し、重複を回避できることに加えて、継承された実装の変更と拡張も容易になります。

確かに、継承に関しては、コンストラクター、保護されたキーワード、上方変換の 3 つが不可欠です。

コンストラクター

子 これまでの説明で、サブクラスが親クラスの属性とメソッドを継承できることはわかりましたが、サブクラスはコンストラクターを継承できないことも同様です。コンストラクターに関しては呼び出しのみ可能であり、継承はできません。 親クラスのコンストラクターを呼び出すには、super() を使用できます。

サブクラスの場合、そのコンストラクターの正しい初期化は非常に重要であり、これを保証する方法が 1 つしかない場合に限ります。それは、コンストラクター内で親クラスのコンストラクターを呼び出して初期化を完了し、親クラスのコンストラクターがすべての知識を持っていることです。および親クラスの初期化を実行するために必要な能力。

public class Person {  
    protected String name;  
    protected int age;  
    protected String sex;  
      
    Person(){  
        System.out.println("Person Constrctor...");  
    }  
}  
  
public class Husband extends Person{  
    private Wife wife;  
  
    Husband(){  
        System.out.println("Husband Constructor...");  
    }  
      
    public static void main(String[] args) {  
        Husband husband  = new Husband();  
    }  
}  
  
Output:  
Person Constrctor...  
Husband Constructor...
ログイン後にコピー

この例から、構築プロセスが親クラスから「外向き」に広がる、つまり、親クラスから開始され、レベルごとに子クラスまで構築が完了することがわかります。また、親クラスのコンストラクターを明示的に参照しませんでした。これが Java の賢い点です。コンパイラーは、デフォルトでサブクラスの親クラスのコンストラクターを呼び出します。

ただし、親クラスのコンストラクターへのこのデフォルトの呼び出しには述語があり、親クラスにはデフォルトのコンストラクターがあります。親クラスにデフォルトのコンストラクターがない場合は、明示的に super() を使用して親クラスのコンストラクターを呼び出す必要があります。そうしないと、コンパイラーは「親クラスの形式に準拠するコンストラクターが見つかりません」というエラーを報告します。

public class Person {  
    protected String name;  
    protected int age;  
    protected String sex;  
      
    Person(String name){  
        System.out.println("Person Constrctor-----" + name);  
    }  
}  
  
public class Husband extends Person{  
    private Wife wife;  
  
    Husband(){  
        super("chenssy");  
        System.out.println("Husband Constructor...");  
    }  
      
    public static void main(String[] args) {  
        Husband husband  = new Husband();  
    }  
}  
  
Output:  
Person Constrctor-----chenssy  
Husband Constructor...
ログイン後にコピー

要約すると: 継承の場合、サブクラスはデフォルトで親クラスのコンストラクターを呼び出しますが、デフォルトの親クラスのコンストラクターがない場合、サブクラスは親クラスのコンストラクターを明示的に指定する必要があります。サブクラスのコンストラクター (コードの最初の行) で実行します。

保護されたキーワード

プライベート アクセス修飾子はカプセル化に最適な選択ですが、これは理想的な世界に基づいているだけであり、場合によってはそのような要件が必要になります。特定のものを可能な限り世界から隠す必要があります。ただし、サブクラスのメンバーがそれらにアクセスすることは許可されています。現時点では、protected を使用する必要があります。

protected の場合、クラス ユーザーに関する限りプライベートであることを示しますが、このクラスを継承するサブクラスまたは同じパッケージ内にある他のクラスからはアクセス可能です。

public class Person {  
    private String name;  
    private int age;  
    private String sex;  
  
    protected String getName() {  
        return name;  
    }  
  
    protected void setName(String name) {  
        this.name = name;  
    }  
  
    public String toString(){  
        return "this name is " + name;  
    }  
      
    /** 省略其他setter、getter方法 **/  
}  
  
public class Husband extends Person{  
    private Wife wife;  
  
    public  String toString(){  
        setName("chenssy");    //调用父类的setName();  
        return  super.toString();    //调用父类的toString()方法  
    }  
  
    public static void main(String[] args) {  
        Husband husband = new Husband();  
          
        System.out.println(husband.toString());  
    }  
}  
  
Output:  
this name is chenssy
ログイン後にコピー

上記の例から、サブクラス夫が親クラス パーソン の setName() を明らかに呼び出すことができることがわかります。

確かに、protected アクセス修飾子を使用して親クラスのプロパティとメソッドへのアクセスを制限することはできますが、最良の方法は、プロパティをプライベートとして保持し (基になる実装を常に変更し続ける必要があります)、プロパティの継承を制御することです。 protected メソッドを介してクラスにユーザーのアクセス権を付与します。上記の相続のところで、猫の相続のIS-Aの相続と動物の関係についてお話しましたので、猫は動物である、あるいは猫は動物であると言えます。このように猫を動物として考えることは、上向きに変化することです。以下のように:

public class Person {  
    public void display(){  
        System.out.println("Play Person...");  
    }  
      
    static void display(Person person){  
        person.display();  
    }  
}  
  
public class Husband extends Person{  
    public static void main(String[] args) {  
        Husband husband = new Husband();  
        Person.display(husband);      //向上转型  
    }  
}
ログイン後にコピー

ここでは person.display(husband) を渡します。この文からも夫が人柄の良い人であることが分かります。


サブクラスを親クラスに変換すると、継承関係が上に移動するため、一般に上方変換と呼ばれます。アップキャストは特殊な型からより一般的な型への変換であるため、発生する可能性のある唯一の変更はプロパティとメソッドの損失です。このため、キャストが明示的に表現されていないか、特別なフラグが指定されていない場合でも、コンパイラは上向きキャストを許可します。

brev

あなたへのアドバイス: 継承は注意して使用してください。


1 1. 親クラスを変更するには、子クラスも変更する必要があります。

2. 継承によりカプセル化が破壊されます。親クラスの実装の詳細はサブクラスに対して透過的です。

3. 継承は強い結合関係です。

したがって、継承を使用するときは、それが実際に効果的で実行可能な方法であることを確認する必要があります。では、継承を使用する必要があるのでしょうか? 「Think in Java」では、サブクラスから親クラスへの上方変換が必要かどうかを自問するという解決策を提供します。上方変換が必要な場合は継承が必要ですが、そうでない場合は継承が必要かどうかを慎重に検討する必要があります。

継承の使用には注意してください。 ! ! ! ! ! ! ! ! ! ! ! ! ! ! ! ! ! ! ! ! ! ! ! ! ! !

上記は「Java の改善 Part 2」の内容です-----Java の 3 つの主要な特性の継承を理解する さらに関連した内容については、PHP 中国語 Web サイト (www.php.cn) に注目してください。 !


関連ラベル:
ソース:php.cn
このウェブサイトの声明
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。
人気のチュートリアル
詳細>
最新のダウンロード
詳細>
ウェブエフェクト
公式サイト
サイト素材
フロントエンドテンプレート