5

私の質問は Java に関するものですが、C# にも適用できます。インスタンス変数をprotectedにするのではなく、privateにすることを誰もが推奨するのはなぜだろうと思っていました。

考えてみましょう。プライベート変数はサブクラスには表示されないため、サブクラスのスーパークラスの変数にアクセスまたは変更する必要がある場合は、getMyPrivateVariableまたはのようなアクセサーおよびミューテーター メソッドを使用する必要があります。setMyPrivateVariable. ただし、一部のクラスを拡張してそのメンバーを継承すると、サブクラスでそれらを直接宣言したかのように機能します。したがって、論理的には、サブクラスもインスタンス変数に直接アクセスできる必要があり、保護された変数を使用してクラスを設計する必要があることを意味します。このような慣行はカプセル化を破ることを理解していますが、これは継承の場合は無関係に思えます。なぜなら、この場合も、スーパークラスのメンバーがサブクラスで宣言されているかのようにすべてが機能するため、サブクラスには「自然な権利」があるからです。継承されているかどうかに関係なく、そのメンバーに直接アクセスできるためです。私の意見では、カプセル化は、オブジェクトの継承ツリーの外部にある他のオブジェクトによってオブジェクトとやり取りするために重要です。

それで、私の質問は、クラスのインスタンス変数を保護ではなくプライベートとして宣言することを誰もが推奨するのはなぜですか?

4

6 に答える 6

1

あなたは自分で答えます-カプセル化。

たとえば、抽象 Cat クラスがあるとします。これは、メンバー変数の速度、つまり実行速度を定義します。

抽象クラスは、明らかに速度を更新する run の final メソッドも定義します。

ここで、Cat のサブクラス (Moggy や Tabby など) が「速度」に直接アクセスして変更できる場合、run メソッドが壊れる可能性があります。

そのため、最初から縛り付けておくのが最善です。必要に応じて、ローカルで宣言することもできます。

于 2013-06-30T18:56:27.970 に答える
0

私見、それは哲学的な質問です。しかし、インスタンス変数へのアクセスに安全層を追加することの問題だと思います。

ゲッターとセッターを介してそれらを公開することにより、クラスの役割に関して正しくアクセスされることを保証します (たとえば、範囲外の値はありません)。また、責任を分離することにより、将来の介入に備えています(たとえば、ある時点で、特定の変数に対して体系的に何らかの処理を行う必要があることに気付いた場合、理論的には他のものに触れず、さらに重要なことに、プログラム全体の機能)。getter メソッドのみを提供することで、それらの一部を読み取り専用に定義する自由もあります。

したがって、基本的には安全性の層が追加され、変数をより細かく制御できます。

さらに、それらはインスタンス変数と呼ばれているため、実際のインスタンスのみがそれらに直接アクセスできることは理にかなっています。

于 2013-08-08T10:20:35.413 に答える
0

サブクラスで継承された変数にアクセスまたは変更する必要がある場合、何らかのアクセサーを使用する必要があります [...]

間違っています:privateメンバーは継承されません。「継承」の意味と、サブクラスのインスタンスがそのスーパークラスのすべてのメンバーを所有しているという事実を混同している可能性があります。

プライベート メンバーが継承されないことが何を意味するかを確認する最善の方法は、サブクラスが独自のプライベート メンバーを宣言する可能性があることを観察することです。これにより、同じ名前のスーパークラスのプライベート メンバーと衝突することは決してありません。二人は平和に共存しています。

メンバーは、サブクラス化によって使用されるように特別にクラスを設計する場合にのみ宣言protectedれます。この場合、メンバーは実際にはパブリック API の一部です。ほとんどのクラスはパブリックな拡張用に設計されていませんが、それらを宣言することは多くの場合オプションではありません。そのようなクラスにすべてのメンバーが含まれている場合、クライアントコードは親に何も追加せずに内部を公開してダミーのサブクラスを自明に作成できるため、それらを作成することと同じです。protectedfinalprotectedpublic

于 2013-06-30T19:15:03.327 に答える
0

インスタンス変数を保護し、クラスをサブクラス化できる場合 (それは ではないためfinal)、誰もがクラスをサブクラス化し、予期しないときにインスタンス変数を変更できます。これにより、機能が意図したとおりに動作しない可能性が非常に高くなります。クラスのさまざまな使用方法に対処する必要があるため、インスタンス変数のすべての可能な変更が、変更された時点で期待される結果を生成することを確認することは非常に困難です。

于 2013-07-01T06:36:50.107 に答える