2009-03-30 8 views
21

私は(C#の場合)ビルダーパターン良い例えば見ているが、私はビルダーパターンを理解していないので、どちらかを見つけることができないか、私がいた何かをしようとしています意図していない。たとえば、車の部品を作成するための抽象的な自動車と抽象的なビルダーメソッドがある場合、私は自分の選択肢のすべてをDirectorに送り、必要な部分を構築してから自分の自動車を作ることができるはずです。どの車、トラック、セミなどが生産されたかに関わらず、私はまったく同じように「駆動」できるはずです。デザインパターン:ビルダー

最初の問題は、具体的な部分のハードコードプロパティ値のほとんどの例ですが、実際にはデータベースから来ていると思います。私はアイデアがディレクター(データソースから)に自分の選択肢を送り、自分のデータに基づいてカスタマイズされた製品をビルダーに作成させることだと思いました。

第2の問題は、実際に部品を作成して、製品に割り当て、文字列を渡すのではなく実際に強く型付けされた製品部品を割り当てることです。

たとえば、私は、ラベル、入力セクション、検証などを含むBuilderの製造フォームフィールドを作成することで、フォームを作成したいと思います。この方法でORMからオブジェクトを読み取ることができますオブジェクトのメタデータを取り出し、これをBuilderに渡し、新しく作成したユーザーコントロールの結果をWebフォームに追加します。

しかし、すべてのBuilderの例では、メインコードからビルダーに選択肢を渡してカスタマイズされた製品を追い出す代わりに、ハードコードされたデータしかありません。すべてが大きな静的事例であるようです。たとえば、それぞれ10個の選択肢を持つ3つのパラメータがある場合、30個の具体的なビルダーメソッドを作成する必要はなく、製品に必要なプロパティを作成するのに十分なものを作成したいだけです。

メインコードにのみDirectorが存在するようにしたいと思っています。パターン内のcase文を使用する代わりに、ポリモーフィズムやメソッドのオーバーロードに似た、どのような具体的なビルダーメソッドを呼び出すかを自動的に判断する方法があります(非常に悪い例ですが)。 (新しい製品タイプを追加するたびに、既存のディレクターを変更する必要がありますが、これは悪いことです)。

+0

おそらく、ビルダーパターンに欠けているのは、最後にオブジェクトが破棄されないということです。パターンをアンスタンスしている場合は、後でこれを追加することをお勧めします。 – Tobias

+0

これらの記事:
[パターンの説明](http://sourcemaking.com/design_patterns/builder)
[c#実装サンプル](http://sourcemaking.com/design_patterns/builder/c%2523)
希望する助けてください。 – 0x49D1

答えて

10

私はWikipediaの記事hereのC#の例を参照しています。

第1の問題は、具体的な部分のハードコードプロパティ値のほとんどの例です。これは実際にはデータベースから来ていると思います。私はアイデアがディレクター(データソースから)に自分の選択肢を送り、自分のデータに基づいてカスタマイズされた製品をビルダーに作成させることだと思いました。

この場合、データベースからデータを取得する方法を知っているPizzaBuilderを実装するクラスがあります。あなたはいくつかの方法でそれを行うことができます。

一つはHawaiianPizzaBuilderを作るだろう。クラスが初期化されると、データベースにハワイアンピザを照会し、その行を取得します。次に、さまざまなBuild(x)メソッドが呼び出されると、取得されたデータベース行の対応するフィールドにプロパティが設定されます。

もう一つは、ちょうどPizzaDatabaseBuilderを行い、あなたがクラスを初期化するとき、あなたはそれをあなたがピザのそのタイプのために必要な行のIDを渡すことを確認してくださいだろう。たとえば、代わりの

waiter.PizzaBuilder = new HawaiianPizzaBuilder(); 

あなたは

waiter.PizzaBuilder = new PizzaDatabaseBuilder("Hawaiian"); 

第二の問題は、私はビルダー方法は、実際の文字列が、実際の強く型付けされた製品を渡さない、製品に割り当て、その後部品を作成したいです使用部品。

は問題ではありません。あなたが必要とするものは、ピザのフィールドを初期化するための他のFactory/Builder型パターンです。 DoughBuilderが適切PizzaDoughを記入し、データベース内の別のテーブルに行くことができる

public override void BuildDough() { pizza.Dough = new PanBakedDoughBuilder(); } 

または

public override void BuildDough() { pizza.Dough = new DoughBuilder("pan baked"); } 

のような例

代わりの

public override void BuildDough() { pizza.Dough = "pan baked"; } 

について、あなたは何をするだろうクラス。

+0

良い答えです。静的に宣言されたファクトリクラスを使用する場合、new演算子は必要ありません。 Tobiaskのビルダー呼び出しもjQueryのように素晴らしいです。答えは、あなたがディレクターを必要としない場合と、私がこのすべてから取っているものです。そのトリックは、それを実際にコード化することです。どうもありがとうございました。 –

+0

この答えを理解すればするほど、RS Conleyがどれくらい知っているか分かります。 :)もし可能なら+100。 –

0

私はあなたが部品の過負荷が少なく、ケース/ ifステートメントをスタックのどこかに持っていることを避けることはできません。また、新しいクラスを追加する際にコードを変更するだけで唯一の選択肢になるかもしれません。

これは、建築プロセスに役立つ工場という他のパターンに役立つと言われています。また、多形性の合理的な使用(例えば、すべての部分がクラスまたはインターフェースである種のものから継承する)は、if/caseおよびoverloadの量を減らすことができる。

これが役に立ちます。

19

ほとんどBuilderパターンの呼び出しは次のようになります。

Car car = new CarBuilder().withDoors(4).withColor("red").withABS(true).build(); 
+2

これは実際にはDesign Patternsで記述されているBuilderパターンではありません。このパターンは、同じソースの異なる表現を作成するように設計されています。たとえば、1つのパーサーを使用しますが、x86、x64、およびJavaバイトコードに異なるバックエンドを持つコンパイラです。 –

+4

これは、デザインパターンでは正確に記述されていない場合がありますが、作成されたオブジェクトにすべてのプロパティが正しく設定されていることを確認します。オブジェクトビルダーに流暢なインターフェースを使用させることもできますが、別の質問の場合は – Kane

10

私はそれについてこのように考えたことがありませんが、LINQ(パターンではなく、構文が)右、実際にビルダーのですか?

これは、クエリを作成し、さまざまな表現(SQL、メモリ内オブジェクトクエリ、Webサービスクエリ、Bart de Smetの実装でさえLinq-Excelへの実装)でクエリを作成するための流暢なインターフェイスです。

+0

はい、もちろんです。 –