Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Builder design pattern: Why do we need a Director?

Recently I've come across the Builder design pattern. It seems that different authors use "Builder pattern" to refer to different flavours, so let me describe the pattern I'm asking about.

We have an algorithm for creating products, i.e., objects of different types. At a sufficiently high level of abstraction the algorithm is the same for all product types, but each product type requires a different implementation of each of the algorithm's abstract steps. For example, we might have the following cake-baking algorithm:

 1. Add liquids.  2. Mix well.  3. Add dry ingredients.  4. Mix well.  5. Pour batter into baking pan.  6. Bake.  7. Return baked cake. 

Different cakes would require different implementations of these steps, i.e., what liquids/dry ingredients to use, what speed to mix at, how long to bake, etc.

The pattern says to do it like so. For each product we create a concrete builder class with an implementation for each of the above steps. All of these classes are derived from an abstract builder base class, which is essentially an interface. So, for example, we will have an abstract base class CakeBaker with pure virtual methods AddLiquid(), MixLiquids(), etc. The concrete cake bakers will be concrete subclasses, e.g.,

class ChocolateCakeBaker : public CakeBaker { public:    virtual void AddLiquids()    {         // Add three eggs and 1 cup of cream    }     virtual void AddDryIngredients()    {        // Add 2 cups flour, 1 cup sugar, 3 tbsp cocoa powder,        // 2 bars ground chocolate, 2 tsp baking powder    }       ...       ... }; 

The LemonCitrusCakeBaker would also be a subclass of CakeBaker, but would use different ingredients and quantities in its methods.

The different cake types will similarly be subclasses of an abstract Cake base class.

Finally, we have a class to implement the abstract algorithm. This is the director. In the bakery example we might call it ExecutiveBaker. This class would accept (from the client) a concrete builder object and use its methods in order to create and return the desired product.

Here's my question. Why do we need the director to be separate from the abstract builder? Why not roll them into a single builder abstract base class, making the original abstract builder's public methods protected (and the concrete subclasses override these as before).

like image 272
Ari Avatar asked Nov 30 '10 11:11

Ari


People also ask

What is the role of director in builder pattern implementation?

Director – The director-class controls the algorithm that generates the final product object. A director object is instantiated and its Construct method is called. The method includes a parameter to capture the specific concrete builder object that is to be used to generate the product.

Why do we need builder design patterns?

The builder pattern is a design pattern designed to provide a flexible solution to various object creation problems in object-oriented programming. The intent of the Builder design pattern is to separate the construction of a complex object from its representation.

What are the consequences of applying the builder design pattern?

Here are key consequences of the Builder pattern: It lets you vary a product's internal representation. The Builder object provides the director with an abstract interface for constructing the product. The interface lets the builder hide the representation and internal structure of the product.

When should we use builder pattern in Java?

The builder pattern, as the name implies, is an alternative way to construct complex objects. This pattern should be used when we want to build different immutable objects using the same object building process. 3.


2 Answers

The core portion of the Builder pattern concerns the Abstract Builder and its subclasses (concrete builders). According to GoF's Design Patterns, director simply "notifies the builder whenever a part of the product should be built", which can be perfectly done by the client.

The StringBuilder class in the Java API is an example of a builder without the respective director -- typically the client class "directs" it.

Also, in Effective Java and Creating and Destroying Java Objects, Joshua Bloch suggests the use of the builder pattern, and he does not include a director.

like image 99
izilotti Avatar answered Oct 13 '22 14:10

izilotti


The GoF variation of the Builder pattern does NOT have the Builder WITHOUT the Director. There's a different point to this, but I'll explain further.

The Builder pattern's point is to give you multiple ways to create the same object. Builder should only have methods which build different parts of an object, but the algorithm - the way these functions are executed - should be the concern of the Director. Without the Director every client would have the need to know EXACTLY how the building works. But with the Director all the Client needs to know is what Builder to use in a specific case.

So, what we have here are two parts:

  1. The Builder, that creates parts of the object one by one. The important thing to note is that for this it keeps state of the created object.
  2. The Director, that controls the way Builder`s functions are executed.

Now to the point I was referring earlier. The Builder part of the pattern is useful in other cases and has been used by different vendors WITHOUT the Director for different purposes. A concrete example of such use would be the Doctrine Query Builder.

The disadvantage of such approach is when the Builder starts to build an object it becomes stateful and if the Client doesn't reset the Builder after the object was created - another Client or the same Client that has been used more than once could get the parts of the object that was created earlier. For this reason, Doctrine uses the Factory pattern to create every instance of the Builder.

I hope this helps those googling.

like image 30
drakonli Avatar answered Oct 13 '22 15:10

drakonli