タグ付けされた質問 「inheritance」

継承は、プログラミング言語のサポートに応じて、既存のオブジェクトのコードを再利用したり、既存のオブジェクトからサブタイプを確立したりする方法です。

5
メソッドを呼び出すことができると定義するよりも、メソッドをオーバーライドできると定義する方が強いコミットメントはありますか?
から:http : //www.artima.com/lejava/articles/designprinciples4.html エーリッヒガンマ:10年経った今でも、それは真実だと思います。継承は、動作を変更するクールな方法です。しかし、サブクラスは、オーバーライドするメソッドが呼び出されるコンテキストについて簡単に推測できるため、脆弱であることがわかっています。私がプラグインするサブクラスコードが呼び出される暗黙的なコンテキストのため、基本クラスとサブクラスの間には密接な結合があります。構成には、より良い特性があります。結合は、いくつかの小さなものをより大きな何かにプラグインするだけで減少し、大きなオブジェクトは小さなオブジェクトをコールバックします。APIの観点から、メソッドをオーバーライドできることを定義することは、メソッドを呼び出すことができることを定義することよりも強力です。 私は彼が何を意味するのか理解していません。誰か説明していただけますか?

5
Java Swingクラスをいつ拡張する必要がありますか?
継承の実装に関する私の現在の理解では、IS-A関係が存在する場合にのみクラスを拡張する必要があります。親クラスがさらに異なる機能を持つより具体的な子タイプを持つことができるが、親で抽象化された共通要素を共有する場合。 私のJava教授が私たちにすべきだと勧めていることのために、私はその理解に疑問を抱いています。彼は、JSwing私たちがクラスで構築しているアプリケーションのために 一つは、すべての拡張する必要がありますJSwingクラス(JFrame、JButton、JTextBox(部品サイズ、部品ラベルなどのような)別のカスタムクラスに、など)と、それらに関連するGUIカスタマイズを指定します これまでのところこれでいいのですが、彼はさらに、すべてのJButtonが独自のカスタム拡張クラスを持つべきであり、唯一の識別要素はラベルであるとアドバイスしています。 たとえば、GUIに2つのボタンOkayとCancelがある場合。彼は、以下のように拡張することを推奨しています。 class OkayButton extends JButton{ MainUI mui; public OkayButton(MainUI mui) { setSize(80,60); setText("Okay"); this.mui = mui; mui.add(this); } } class CancelButton extends JButton{ MainUI mui; public CancelButton(MainUI mui) { setSize(80,60); setText("Cancel"); this.mui = mui; mui.add(this); } } ご覧のとおり、唯一の違いはsetText機能にあります。 それでは、この標準的な慣習はありますか? ところで、これが議論されたコースは、Javaのベストプログラミングプラクティスと呼ばれています [教授からの返信] そこで私は教授と問題について話し合い、答えに挙げられているすべての点を挙げました。 彼の正当性は、サブクラス化がGUI設計標準に従って再利用可能なコードを提供することです。たとえば、開発者が1つのウィンドウでカスタムボタンOkayとCancelボタンを使用している場合、同じボタンを他のウィンドウにも配置する方が簡単です。 理由はわかりますが、それでも継承を利用してコードを脆弱にしているだけです。 後で、開発者はボタンを誤って呼び出して変更setTextする可能性がありOkayます。その場合、サブクラスは単に迷惑になります。


3
通常、Java開発にはC#/。NETよりも多くのサブクラスが含まれますか?
最近、Androidの開発を検討し始めました。これにより、私はJavaソフトウェア開発の世界に戻ってきました。私が最後にJavaで作業したときは、OOPを(私が思うに)今ほど理解していないことを認めます。 私のキャリアでは主にC#を使用していましたが、継承がJavaとC#を使用する方法に驚くべき違いがあることに気付きました。 C#では、ほとんどの状況で継承を回避できるように思われました。通常、当面のタスクは、.NETフレームワークの具体的なクラスを使用して実現できます。 Javaでは、コードサンプルから収集したものから、Javaフレームワークは多くのインターフェイスまたは抽象クラスを提供し、開発者が実装/拡張することを意図しているようです。 これは、スタイルにまで煮詰めるには大きすぎる違いのようです。この背後にある理由は何ですか?これを理解するまで、きれいなJavaコードを書くことはできないと思います。 また、これはAndroid SDKだけに限定されていますか?これはOOPに対するJava全体のアプローチですか? または別の言い方をすれば、 これら2つの言語の設計について、他の言語よりも多かれ少なかれ継承を使用しているように思われますか? 言語が継承を同一に扱い、私の観察が有効であると仮定すると、これは言語ではなくフレームワーク/ライブラリの設計に関連することを意味します。この種のデザインの動機は何でしょうか?

5
Pythonミックスインはアンチパターンですか?
私はpylint、他の静的分析ツールがすべてを知っているわけではないことを完全に認識しています。(これは、conventions だけでなく、さまざまなクラスのメッセージに適用されます。) 私のようなクラスがある場合 class related_methods(): def a_method(self): self.stack.function(self.my_var) class more_methods(): def b_method(self): self.otherfunc() class implement_methods(related_methods, more_methods): def __init__(self): self.stack = some() self.my_var = other() def otherfunc(self): self.a_method() 明らかに、それは不自然です。あなたが好きなら、これはより良い例です。 このスタイルは「ミックスイン」を使用して呼び出されると思います。 他のツールと同様に、pylintレートでこのコードを-21.67 / 10、主にそれは考えているためmore_methodsとrelated_methods持っていないselfか、属性otherfunc、stack、annd my_varのコードを実行せず、それは明らかに見ることができないためrelated_methodsとmore_methods混合でにしていますimplement_methods。 コンパイラーと静的解析ツールが停止問題を常に解決できるとは限りませんが、これは確かに、継承されたものを見るとimplement_methodsこれが完全に有効であることを示す場合であり、それは非常に簡単なことです。 なぜ静的解析ツールがこの有効な(私が思うに)OOPパターンを拒否するのですか? どちらか: 彼らは継承をチェックしようとさえしません mixinは慣用的で読みやすいPythonでは推奨されません #1は明らかに間違っています。なぜなら、を使用し pylintて継承する私のクラス(でのみ定義されているもの)について教えてもらえば、文句を言わないからです。unittest.TestCaseself.assertEqualunittest.TestCase ミックスインは非Pythonpythonですか、落胆しますか?

10
サブクラスのAPIを汚染する場合でも、自分自身をキャストするオブジェクトを使用しても大丈夫ですか?
基本クラスがありBaseます。2つのサブクラスとがSub1ありSub2ます。各サブクラスにはいくつかの追加メソッドがあります。たとえば、Sub1has Sandwich makeASandwich(Ingredients... ingredients)、およびSub2has boolean contactAliens(Frequency onFrequency)。 これらのメソッドは異なるパラメーターを取り、まったく異なることを行うため、完全に互換性がなく、この問題を解決するためにポリモーフィズムを使用することはできません。 Baseほとんどの機能を提供し、Baseオブジェクトの大規模なコレクションを持っています。ただし、すべてのBaseオブジェクトはa Sub1またはaのいずれかSub2であり、時にはそれらがどれであるかを知る必要があります。 次のことを行うのは悪い考えのようです。 for (Base base : bases) { if (base instanceof Sub1) { ((Sub1) base).makeASandwich(getRandomIngredients()); // ... etc. } else { // must be Sub2 ((Sub2) base).contactAliens(getFrequency()); // ... etc. } } そこで、キャストせずにこれを回避する戦略を思いつきました。 Base現在、これらのメソッドがあります: boolean isSub1(); Sub1 asSub1(); Sub2 asSub2(); そしてもちろん、Sub1これらのメソッドを次のように実装します …

7
コンストラクターが継承されないのはなぜですか?
コンストラクターが基本クラスから継承された場合、どのような問題が発生する可能性があるのか​​、私は混乱しています。Cpp Primer Plusによると、 コンストラクターは他のクラスメソッドとは異なり、新しいオブジェクトを作成しますが、他のメソッドは既存のオブジェクトによって呼び出されます。これが、コンストラクターが継承されない理由の1つです。継承とは、派生オブジェクトが基本クラスメソッドを使用できることを意味しますが、コンストラクターの場合、コンストラクターが作業を完了するまでオブジェクトは存在しません。 オブジェクトの構築が完了する前にコンストラクターが呼び出されることを理解しています。 子クラスが継承する場合、どうすれば問題につながる可能性があります(継承することで、子クラスが親クラスメソッドをオーバーライドできることを意味します。 オブジェクトを作成するときを除いて、コード内から明示的にコンストラクターを呼び出す必要はないことを理解しています(まだ気づいていません)。その場合でも、何らかのメカニズムを使用して、親コンストラクタを呼び出すことができます[cppでは、使用::または使用member initialiser list、javaでは使用super]。Javaでは、1行目で呼び出す強制があります。最初に親オブジェクトを作成してから、子オブジェクトの構築を続行することを理解しています。 それを無効にすることができます。しかし、私はこれが問題を引き起こす可能性がある状況を思い付くことができません。子が親コンストラクタを継承しない場合、何が問題になる可能性がありますか? これは、不要な関数を継承しないようにするためです。それとももっとありますか?
33 c++  inheritance 

10
「親x = new Child();」ではなく「親x = new Child();」は、後者を使用できる場合の悪い習慣ですか?
たとえば、次のようなフラグメントを作成するコードを見たことがあります。 Fragment myFragment=new MyFragment(); MyFragmentではなくFragmentとして変数を宣言します。MyFragmentはFragmentの子クラスです。このコードは次のようにすべきだと思うので、このコード行を満足していません MyFragment myFragment=new MyFragment(); より具体的ですが、本当ですか? または質問の一般化では、使用するのは悪い習慣ですか? Parent x=new Child(); の代わりに Child x=new Child(); 前者をコンパイルエラーなしで後者に変更できるとしたら?


7
継承されたメソッドをテストする必要がありますか?
基本クラスEmployeeから派生したクラスManagerがあり、そのEmployeeにはManagerによって継承されるメソッドgetEmail()があるとします。マネージャーのgetEmail()メソッドの動作が実際に従業員のものと同じであることをテストする必要がありますか? これらのテストが作成された時点で動作は同じになりますが、もちろん将来のある時点で誰かがこのメソッドをオーバーライドし、その動作を変更して、アプリケーションを中断するかもしれません。しかし、本質的に干渉コードがないことをテストするのは少し奇妙に思えます。 (Manager :: getEmail()メソッドをテストしても、Manager :: getEmail()が作成/オーバーライドされるまで、コードカバレッジ(または他のコード品質メトリック(?))は改善されません。) (答えが「はい」の場合、基本クラスと派生クラス間で共有されるテストの管理方法に関する情報が役立ちます。) 質問の同等の定式化: 派生クラスが基本クラスからメソッドを継承する場合、継承されたメソッドが次のことを期待しているかどうかをどのように表現(テスト)しますか? 現在のベースとまったく同じように動作します(ベースの動作が変更されても、派生メソッドの動作は変更されません)。 常にベースとまったく同じように動作します(ベースクラスの動作が変わると、派生クラスの動作も変わります)。または ただし、必要に応じて動作します(呼び出さないため、このメソッドの動作は気にしません)。

4
プロトタイプ継承は、従来の継承と実際にどのように異なりますか?
継承、ポリモーフィズム、およびカプセル化は、OOPの3つの最も明確で重要な機能であり、それらから、最近では継承に高い使用統計があります。私はJavaScriptを学んでいますが、ここでは彼らはすべてプロトタイプ継承を持っていると言い、どこでも人々はそれが古典的な継承とはまったく異なるものだと言います。 しかし、実際の使用の点との違いは理解できませんか?つまり、基本クラス(プロトタイプ)を定義し、そこからいくつかのサブクラスを派生させると、どちらも基本クラスの機能にアクセスでき、派生クラスの機能を拡張できます。私が言ったことを継承の意図した結果であると考える場合、プロトタイプバージョンとクラシックバージョンのどちらを使用しているのかを気にする必要があるのはなぜですか? さらに明確にするために、プロトタイプ継承と従来の継承の有用性と使用パターンに違いは見られません。その結果、両者が同じものであるOOADをもたらすため、それらが異なる理由を学ぶことに興味がありません。プロトタイプの継承は、実際には(理論的にではなく)古典的な継承とどの程度異なりますか?

5
多くの小さなクラスと論理的な(しかし)複雑な継承
優れたOOPデザイン、クリーンなコード、柔軟性、将来のコードのにおいを避けるという点で、何が優れているのだろうかと思っています。イメージの状況。クラスとして表す必要がある非常によく似たオブジェクトがたくさんあります。これらのクラスには特定の機能はなく、データクラスだけで、名前(およびコンテキスト)だけが異なります。例: Class A { String name; string description; } Class B { String name; String count; String description; } Class C { String name; String count; String description; String imageUrl; } Class D { String name; String count; } Class E { String name; String count; String imageUrl; String age; …

3
継承のないオブジェクト指向言語はありますか?
今日のコードレビューの間に、私の同僚は何か面白いことを言った。 prototypeは、継承が必要な場合にのみ役立ちます- いつ継承が良いアイデアですか? 私はこれについて考え、私は通常、継承を使用して、最初はひどく設計されたコードを回避することに気付きました。現代のオブジェクト指向スタイルは継承よりも合成を好みますが、これを心に留めて実際に強制した言語は知りません。 クラス、オブジェクト、メソッド、インターフェースなどを備えた汎用プログラミング言語はありますか?クラスベースの継承を禁止しますか?(このような考えが意味をなさない場合、なぜですか?)

3
共通の機能を共有するWindowsフォームに最適な設計
過去に、アプリケーションでWindowsフォームの拡張を許可するために継承を使用しました。すべてのフォームに共通のコントロール、アートワーク、および機能がある場合、共通のコントロールと機能を実装する基本フォームを作成し、他のコントロールがその基本フォームから継承できるようにします。ただし、その設計にはいくつかの問題があります。 コントロールは一度に1つのコンテナにしか入れることができないため、静的なコントロールは扱いにくいものになります。たとえば、このクラスの他の(派生)インスタンスがすべて同じTreeViewを変更および表示できるように、保護および静的にするTreeViewを含むBaseFormというベースフォームがあるとします。TreeViewは一度に1つのコンテナにしか入れることができないため、これはBaseFormから継承する複数のクラスでは機能しません。おそらく初期化された最後のフォームにあります。すべてのインスタンスはコントロールを編集できますが、一度に1つだけ表示されます。もちろん、回避策はありますが、それらはすべていものです。(これは私にとって本当に悪い設計のようです。なぜ複数のコンテナが同じオブジェクトへのポインタを格納できないのでしょうか?とにかく、それがそうです。) フォーム間の状態、つまり、ボタンの状態、ラベルテキストなど、グローバル変数を使用して、Loadの状態をリセットする必要があります。 これは、Visual Studioのデザイナーによって実際にサポートされていません。 使用するのに優れた、それでも簡単に保守可能な設計はありますか?または、フォームの継承が依然として最善のアプローチですか? 更新 MVCからMVPに、オブザーバーパターンからイベントパターンに移動しました。ここに私が今考えているものがあります、批評してください: BaseFormクラスには、コントロールと、それらのコントロールに接続されたイベントのみが含まれます。それらを処理するために何らかのロジックが必要なすべてのイベントは、すぐにBaseFormPresenterクラスに渡されます。このクラスは、UIからのデータを処理し、論理演算を実行してから、BaseFormModelを更新します。モデルは、状態の変更時に発生するイベントをPresenterクラスに公開し、Presenterクラスはサブスクライブ(または監視)します。プレゼンターはイベント通知を受け取ると、ロジックを実行し、それに応じてビューを変更します。 メモリには各Modelクラスが1つしかありませんが、BaseFormの多くのインスタンス、したがってBaseFormPresenterが存在する可能性があります。これにより、BaseFormの各インスタンスを同じデータモデルに同期するという私の問題が解決します。 質問: どのレイヤーが最後に押されたボタンのようなものを保存する必要があるので、フォーム間でユーザーのために強調表示し続けることができます(CSSメニューのように)? このデザインを批判してください。ご協力いただきありがとうございます!

3
事前条件の強化と事後条件の弱化は、リスコフ代替原理にどのように違反しますか?
次の場合、リスコフの置換原則に違反していると読みました。 前提条件が強化されている、または 事後条件が弱体化 しかし、これらの2つの点がリスコフの代替原則にどのように違反するかは、まだ完全にはわかりません。例を挙げて説明してください。具体的には、上記の条件のいずれかが、サブクラスオブジェクトをスーパークラスオブジェクトに置き換えることができない状況をどのように引き起こしますか?

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.