タグ付けされた質問 「object-oriented-design」

オブジェクト指向設計とは、ソフトウェアの問題を解決するために、相互作用するオブジェクトのシステムを計画するプロセスです。

6
関数型プログラミングは、問題と解決策の間の「代表的なギャップ」を増やしますか?[閉まっている]
閉じた。この質問はより集中する必要があります。現在、回答を受け付けていません。 この質問を改善したいですか?この投稿を編集するだけで1つの問題に焦点を当てるように質問を更新します。 4年前に閉鎖されました。 機械言語(例:)は、0110101000110101一般にコンピューター言語がより高度な抽象化に進化してきたため、一般的に問題に適用されたときにコードを理解しやすくします。アセンブラーはマシンコードの抽象化であり、Cはアセンブラーの抽象化などでした。 オブジェクト指向設計は、オブジェクトの観点から問題をモデル化するのに非常に優れているようです。たとえば、大学の履修登録システムの問題は、Courseクラス、Studentクラスなどでモデル化できます。 OO言語では、責任を負う同様のクラスがあり、一般に設計、特にコードのモジュール化に役立ちます。この問題をOOメソッドで解決する10の独立したチームに与えた場合、通常、10のソリューションには共通して問題に関連するクラスがあります。これらのクラスの結合と相互作用を開始し始めると、多くの違いが生じる可能性があるため、「表現のギャップがゼロ」というものはありません。 関数型プログラミングの私の経験は非常に限られています(実際の使用はなく、Hello Worldタイプのプログラムのみ)。このような言語がOO言語のようにFPソリューションを問題に(低い表現のギャップで)簡単にマッピングできるようにする方法を私は見ていません。 並行プログラミングに関するFPの利点を理解しています。しかし、私は何かを逃していますか、またはFPは表現のギャップを減らすことではありませんか? これを尋ねる別の方法:同じ現実の問題を解決する10の異なるチームのFPコードには多くの共通点がありますか? 抽象化に関するウィキペディア(コンピューターサイエンス)から(強調鉱山): 関数型プログラミング言語は一般に、ラムダ抽象化(用語を変数の関数にする)、高次関数(パラメーターは関数)、ブラケット抽象化(用語を変数の関数にする)など、関数に関連する抽象化を示します。 [一部の]実際の問題はこのような抽象化では簡単にモデル化されないため、表現のギャップは潜在的に拡大する可能性があります。 表現のギャップを減らすもう1つの方法は、ソリューション要素を問題にまでさかのぼることです。0さんと1マシンコードでSは一方で、バックトレースすることは非常に困難であるStudentクラスは、トレースバックに簡単です。すべてのOOクラスが問題空間に簡単にトレースできるわけではありませんが、多くのクラスがトレースしています。 FPの抽象化は、常に彼らが(離れてから解決されている問題空間のどの部分を見つけるために説明する必要はありません数学の問題)?OK-私はこの部分でいいです。さらに多くの例を見ると、FPの抽象化がデータ処理で表現される問題の一部に対して非常に明確であることがわかります。 関連する質問に対する受け入れられた回答UMLは、機能プログラムのモデル化に使用できますか?-「機能プログラマーは、ダイアグラムをあまり使いません」と言います。それがUMLであるかどうかは本当に気にしませんが、広く使用されているダイアグラムがない場合、FPの抽象化が簡単に理解/通信できるかどうか疑問に思います(この答えが正しいと仮定して)。繰り返しになりますが、FPの使用/理解のレベルはささいなものなので、単純なFPプログラムのダイアグラムの必要はないと理解しています。 OOデザインには、機能/クラス/パッケージレベルの抽象化があり、それぞれにカプセル化(アクセス制御、情報隠蔽)があり、複雑さの管理を容易にします。これらは、問題から解決策へと簡単に戻ることができる要素です。 多くの答えは、オブジェクト指向に類似した方法でFPで分析と設計が行われる方法について述べていますが、これまで高レベルのものを引用する人はいません(paulはいくつかの興味深いものを引用しましたが、低レベルです)。昨日はグーグルで多くのことをして、興味深い議論を見つけました。以下は、サイモン・トンプソンによるリファクタリング機能プログラムからのものです(2004)(強調の鉱山) オブジェクト指向システムの設計では、プログラミングよりも設計が優先されることは当然のことです。デザインは、EclipseなどのツールでサポートされているUMLのようなシステムを使用して作成されます。初心者のプログラマーは、BlueJのようなシステムを使用して視覚的な設計アプローチを学ぶことができます。関数型プログラミングのための同様の方法論に関する作業がFAD:Functional Analysis and Designで報告されていますが、他の作業はほとんどありません。これにはいくつかの理由があります。 既存の機能プログラムは、設計を必要としない規模です。多くの機能プログラムは小さいですが、Glasgow Haskell Compilerなどの他のプログラムはかなりのものです。 機能プログラムはアプリケーションドメインを直接モデル化するため、デザインは無関係になります。関数型言語はさまざまな強力な抽象化を提供しますが、これらが現実世界をモデル化するために必要なすべての抽象化のみを提供すると主張することは困難です。 機能プログラムは、進化する一連のプロトタイプとして構築されます。 上記で引用された博士論文では、分析と設計の方法論(ADM)を使用する利点が、パラダイムとは無関係に概説されています。しかし、ADMは実装パラダイムと整合する必要があるという主張がなされています。つまり、OOADMはOOプログラミングに最適であり、FPなどの別のパラダイムにはあまり適用されません。これは、私が表現ギャップと呼ぶものを言い換えていると思う素晴らしい引用です: どのパラダイムがソフトウェア開発に最適なサポートを提供するかについては長々と議論できますが、問題の説明から実装および配信まで単一のパラダイム内にとどまると、最も自然で効率的かつ効果的な開発パッケージを実現できます。 FADが提案する一連の図を次に示します。 実装で使用する関数を関数に提示する関数依存図。 型に同じサービスを提供する型依存図。そして、 システムのモジュールアーキテクチャのビューを表示するモジュール依存関係図。 FAD論文のセクション5.1にはケーススタディがあります。これは、フットボール(サッカー)リーグに関連するデータの生成を自動化するシステムです。要件は100%機能的です。たとえば、サッカーの結果の入力、リーグテーブルの作成、得点表、出欠表、チーム間での選手の移動、新しい結果の後のデータの更新などです。 、「新しい機能は最小限のコストで許可する必要がある」と述べることは別として、テストすることはほぼ不可能です。 悲しいことに、FADを除いて、FP用に提案されているモデリング言語(視覚)の最新の参照はありません。UMLは別のパラダイムなので、それを忘れてください。

6
多重継承は単一責任原則に違反しますか?
2つの異なるクラスから継承するクラスがある場合、これはサブクラスが(少なくとも)2つのことを自動的に行うことを意味しないのですか?各スーパークラスから1つですか? 複数のインターフェイス継承がある場合、違いはないと思います。 編集:明確にするために、複数のクラスをサブクラス化するとSRPに違反する場合、複数の(マーカーまたは基本インターフェイス(Comparableなど))インターフェイスの実装もSRPに違反すると考えています。

3
状態パターンは、リスコフ代替原理に違反していますか?
この画像は、ドメイン駆動のデザインとパターンの適用:C#および.NETの例を使用したものです。 これは、a がその存続期間中に異なる状態を持つことができる状態パターンのクラス図ですSalesOrder。異なる状態間では特定の遷移のみが許可されます。 これでOrderStateクラスはabstractクラスになり、そのすべてのメソッドはそのサブクラスに継承されます。Cancelled他の状態への遷移を許可しない最終状態であるサブクラスを考慮する場合override、このクラスのすべてのメソッドで例外をスローする必要があります。 サブクラスは親の振る舞いを変えてはいけないので、今ではそれはリスコフの代用原則に違反していないのですか?抽象クラスをインターフェイスに変更すると、これが修正されますか? これはどのように修正できますか?

5
SRP(単一責任原則)は客観的ですか?
「ユーザーにとって魅力的な」デザインをデザインしたい2人のUIデザイナーを考えてみましょう。「ユーザーの魅力」は、客観的ではなく、デザイナーの心の中にのみ存在する概念です。したがって、デザイナーAはたとえば赤を選択し、デザイナーBは青を選択できます。デザイナーAは、デザイナーBとはまったく異なるレイアウトを作成します。 SRP(Single Responsibility Principle)について読みましたが、私が理解したのは、OOデザイナーから別のOOデザイナーまでさまざまな主観的な分析または責任の内訳です。私は正しいですか?言い換えれば、SRPプリンシパルに基づいて1つのシステムに対して2つの異なる設計を思いつく2つの優れたオブジェクト指向アナライザーとデザイナーを使用することは可能ですか?

4
Java-完全に静的なクラスを持つことは悪い考えですか?
私は現在、より大きなソロプロジェクトに取り組んでおり、インスタンスを作成する理由がわからないクラスがいくつかあります。 たとえば、現在のダイスクラスはすべてのデータを静的に格納し、そのメソッドもすべて静的です。サイコロを転がして新しい値を取得したいときは、を使用するだけなので、初期化する必要はありませんDice.roll()。 私はこのような主な機能を1つだけ持っているいくつかの類似したクラスを持ち、すべてのイベントを担当する一種の「コントローラー」クラスで作業を開始しようとしています(プレイヤーが移動したとき、そうです)、このクラスでも同じ考えに従うことができることがわかりました。これらの特定のクラスに対して複数のオブジェクトを作成する予定はないので、それらを完全に静的にすることは悪い考えでしょうか? Javaに関しては、これが「悪い習慣」と見なされるのかと思っていました。私が見たものから、コミュニティはこのトピックに関して一種の分裂のように思われますか?とにかく、私はこれに関するいくつかの議論が大好きだし、リソースへのリンクも素晴らしいでしょう!

4
JavaScriptの関数の謎を解決できません
私は、Javascriptのカーテンシーンの背後にあるものを理解しようとしています。組み込みオブジェクト、特にオブジェクトと関数、およびそれらの間の関係の作成を理解することに固執しています。 Array、Stringなどのすべての組み込みオブジェクトがObjectの拡張(継承)であると読んだとき、Objectは作成された最初の組み込みオブジェクトであり、残りのオブジェクトはそれを継承すると仮定しました。しかし、オブジェクトは関数によってのみ作成できることを知ったとき、それは意味がありませんが、関数も関数のオブジェクトにすぎません。鶏と鶏のジレンマのように聞こえ始めました。 他の非常に紛らわしいことは、console.log(Function.prototype)関数を印刷console.log(Object.prototype)するのに、印刷するときにオブジェクトを印刷する場合です。Function.prototype関数がオブジェクトであることが意図されていたのになぜですか? また、Mozillaのドキュメントによれば、すべてのjavascript functionはFunctionオブジェクトの拡張ですが、あなたconsole.log(Function.prototype.constructor)が再び関数である場合はそうです。では、何かを使用して自分自身を作成するにはどうすればよいでしょう(Mind = blown)。 最後にFunction.prototype、関数ですが、doesをconstructor使用Function.prototype.constructorして関数にアクセスできます。つまりFunction.prototype、prototypeオブジェクトを返す関数です

5
自身または他の2つのことを表すデータ型を作成する方法
バックグラウンド 私が取り組んでいる実際の問題は次のとおりです。カードゲームMagic:The Gatheringでカードを表現する方法が必要です。ゲーム内のほとんどのカードは見た目が普通のカードですが、一部は2つの部分に分かれており、それぞれに名前が付いています。これらの2部構成のカードの各半分は、カード自体として扱われます。そのため、明確にするためにCard、通常のカード、または2部構成のカードの半分(つまり、名前が1つだけのカード)を参照するためにのみ使用します。 したがって、基本タイプのCardがあります。これらのオブジェクトの目的は、実際には単にカードのプロパティを保持することです。彼らは本当に自分で何もしません。 interface Card { String name(); String text(); // etc } には2つのサブクラスがありCard、私はこれを呼び出していますPartialCard(2部構成のカードの半分)とWholeCard(通常のカード)。 PartialCardには2つの追加メソッドがあります:PartialCard otherPart()とboolean isFirstPart()。 代表者 私がデッキを持っている場合、それはWholeCardsではなくCardsで構成されている必要Cardがあり、a はである可能性がありPartialCard、それは意味がありません。そのため、「物理カード」を表すオブジェクト、つまり1つWholeCardまたは2つPartialCardのsを表すことができるオブジェクトが必要です。私は暫定的にこのタイプを呼んでいるRepresentative、とCard方法を持っているでしょうgetRepresentative()。Aは、Representativeカード(複数可)にほとんど直接的な情報を提供するだろう、それはそれ/それらへの唯一のポイントだろう、を表します。今、私の素晴らしい/クレイジー/愚かなアイデア(あなたが決める)は、WholeCardがとの両方 Cardを継承するということですRepresentative。結局のところ、彼らは自分自身を表すカードです!WholeCardsはgetRepresentativeとして実装できますreturn this;。 に関してはPartialCards、それらは自分自身を表しRepresentativeてはいませんが、a Cardではなく、2つPartialCardのにアクセスするためのメソッドを提供する外部を持っています。 このタイプの階層は理にかなっていると思いますが、複雑です。Cardsを「概念的なカード」と考え、Representativesを「物理的なカード」と考えると、ほとんどのカードは両方です。物理的なカードには実際には概念的なカードが含まれており、それらは同じものではないと主張することができると思いますが、私はそれらが同じだと主張します。 型キャストの必要性 のでPartialCard、SとWholeCardsともにCard、S、及びそれらを分離するためには良い理由は、通常はありません、私は通常、ちょうどと仕事ができると思いますCollection<Card>。そのPartialCardため、追加のメソッドにアクセスするためにs をキャストする必要がある場合があります。今は、明示的なキャストが本当に好きではないので、ここで説明するシステムを使用しています。そしてのようにCard、それらが表す実際のにアクセスするにはRepresentative、WholeCardまたはのいずれかにキャストする必要があります。CompositeCard 要約のために: ベースタイプ Representative ベースタイプ Card タイプWholeCard extends Card, Representative(アクセスは不要、それ自体を表す) タイプPartialCard extends Card(他の部分へのアクセスを許可) タイプComposite extends Representative(両方の部分にアクセスできます) これは非常識ですか?実際にはかなり理にかなっていると思うが、正直なところわからない。

1
訪問者パターンを理解する
GUIコントロールを表すクラスの階層があります。このようなもの: Control->ContainerControl->Form さまざまなことを行うオブジェクトで動作する一連のアルゴリズムを実装する必要があり、Visitorパターンが最もクリーンなソリューションになると考えています。たとえば、オブジェクトの階層のXML表現を作成するアルゴリズムを考えてみましょう。「クラシック」アプローチを使用して、私はこれを行います: public abstract class Control { public virtual XmlElement ToXML(XmlDocument document) { XmlElement xml = document.CreateElement(this.GetType().Name); // Create element, fill it with attributes declared with control return xml; } } public abstract class ContainerControl : Control { public override XmlElement ToXML(XmlDocument document) { XmlElement xml = base.ToXML(document); // …

6
オブジェクト指向設計における疎結合
私はGRASPを学ぼうとしていますが、これは低結合について説明されています(ここ3ページにあります)。 クラスのメソッドaddTrackについて考えてみましょうAlbum。2つの可能なメソッドは次のとおりです。 addTrack( Track t ) そして addTrack( int no, String title, double duration ) どの方法で結合が減少しますか?Albumクラスを使用するクラスはTrackクラスを知る必要がないので、2番目のものはそうします。一般に、メソッドへのパラメーターは、java。*パッケージの基本型(int、char ...)およびクラスを使用する必要があります。 私はこれに反対する傾向があります。私はさまざまな理由addTrack(Track t)よりも優れていると信じていますaddTrack(int no, String title, double duration): メソッドのパラメーターはできるだけ少ないほうが常に良いです(Uncle BobのClean Codeによれば、なしまたは1つ、できれば2、場合によっては3、特別な場合は3、3つ以上はリファクタリングが必要です-これらはもちろん推奨ルールではありません) 。 場合addTrackのインタフェースの方法であり、要件がいることを必要とするTrackより多くの情報(たとえば年またはジャンル)を持っている必要があり、インターフェイスを変更する必要があるので、この方法は、別のパラメータがサポートする必要があること。 カプセル化が壊れています。addTrackがインターフェイス内にある場合、の内部を知らないはずTrackです。 実際には、多くのパラメーターを使用して、2番目の方法でより結合されています。仮定noから変更するパラメータニーズをintへlong以上があるのでMAX_INT、トラック(または何らかの理由で)。Trackメソッドとメソッドの両方を変更する必要がありますが、メソッドaddTrack(Track track)のみTrackが変更される場合は変更します。 4つの引数はすべて実際には相互に関連しており、それらの一部は他からの結果です。 どのアプローチが良いですか?

2
PHPの違法:OOP設計の理由はありますか?
以下のインターフェースの継承はPHPでは違法ですが、実際にはかなり役に立つと思います。以下のデザインに実際のアンチパターンまたは文書化された問題がありますか?PHPは私を保護していますか? <?php /** * Marker interface */ interface IConfig {} /** * An api sdk tool */ interface IApi { public __construct(IConfig $cfg); } /** * Api configuration specific to http */ interface IHttpConfig extends IConfig { public getSomeNiceHttpSpecificFeature(); } /** * Illegal, but would be really nice to have. …

6
戦略パターンの利点
if / thenの場合にコードを書くことができるのに、なぜ戦略パターンを使用するのが有益なのですか? 例:TaxPayerクラスがあり、そのメソッドの1つが異なるアルゴリズムを使用して税金を計算します。では、なぜif / thenケースを持ち、戦略パターンを使用する代わりに、そのメソッドで使用するアルゴリズムを見つけられないのでしょうか?また、なぜTaxPayerクラスの各アルゴリズムに個別のメソッドを実装できないのですか? また、実行時にアルゴリズムが変更されるとはどういう意味ですか?

6
抽象クラス、インターフェースの違い、およびそれらをいつ使用するか
最近、私は頭をOOPに巻きつけ始めました。そして今、抽象クラスとインターフェースの違いについて読むほど、混乱してしまいます。これまでのところ、どちらもインスタンス化できません。インターフェースは多かれ少なかれ構造的な青写真であり、スケルトンを決定し、抽象は部分的にコードを実装できることによって異なります。 私の特定の状況を通して、これらについてもっと学びたいです。背景情報をもう少し知りたい場合の最初の質問へのリンクは次のとおりです。新しいクラスに適した設計モデルは何ですか? ここに私が作成した2つのクラスがあります。 class Ad { $title; $description $price; function get_data($website){ } function validate_price(){ } } class calendar_event { $title; $description $start_date; function get_data($website){ //guts } function validate_dates(){ //guts } } ご覧のとおり、これらのクラスはほぼ同じです。ここに示されているが、他の機能があるではないlike get_zip()、save_to_database()私のクラスで共通しています。また、すべての一般的なメソッドと、もちろんそれらのクラスに固有のプロパティ(マイレージ、重量など)を持つ他のクラスのCarsとPetsを追加しました。 現在、DRYの原則に違反しており、複数のファイルにわたって同じコードを管理および変更しています。私は、ボート、馬、またはその他のようなクラスを増やすつもりです。 これは、インターフェイスまたは抽象クラスを使用する場所ですか?抽象クラスについて理解していることから、抽象クラスにすべての共通要素が組み込まれたテンプレートとしてスーパークラスを使用し、将来のクラスで特に必要な項目のみを追加します。例えば: abstract class content { $title; $description function get_data($website){ } function common_function2() { } function common_function3() …

6
インターフェイスメソッドを抽象メソッドと見なすことはできますか?
私はそれについて考えていた、と私はいくつかの疑問がありました。 たとえば、インターフェイスを宣言するとき: public interface MyInterface { public void method1(); public void method2(); } これらのインターフェイスメソッドは抽象と見なされますか?つまり、抽象メソッドの概念は次のとおりです。 抽象メソッドは宣言されたメソッドですが、実装は含まれていません。 だから、これらのメソッドは抽象的と見なすことができますか?私はabstract言葉を使っていないので、それらは「純粋な」抽象メソッドではありませんが、概念的にはそうであるように見えます。 それについて何か教えていただけますか? ありがとう。


2
リポジトリは本当に何をすべきでしょうか?
リポジトリパターンの多くを聞いたことがありますが、リポジトリが実際に何をすべきかを理解していませんでした。「リポジトリが実際にすべきこと」と言うとき、私は主にどのメソッドを提供すべきかを心配しています。たとえば、リポジトリは本当にCRUDメソッドを提供する必要がありますか、それとも何らかの種類のメソッドを提供する必要がありますか? つまり、リポジトリにビジネスロジックを含めるべきですか、それとも単にデータストアと通信し、保存またはロードするエンティティを管理するためのロジックを含めるべきですか? また、リポジトリは集約の永続性の単位であると聞いています。しかし、それはどうですか?これが実際にどのように機能するのか理解できません。IRepositoryCRUDメソッドを含むインターフェイスを1つだけ持つ必要があると考えました。その後、エンティティには、そのような型をデータストアから保存および取得するためのロジックが含まれます。

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