Builder Design Pattern

The purpose of Builder Design Pattern is to separate the construction of complex object from its representation so that the same construction process can create different representation. It is usually use in building complex objects by using a step by step approach.

The best practical example I could think is Language Translator. Where there are series of steps involved before language can be translated (such as parsing of text, lexical analysis, grammar, etc) .  But I won’t use this to explain this pattern.

UML Diagram

Figure 1: UML Class Diagram for Builder Design Pattern

Participants
Class/Interface Description
Director Uses the ConcreteBuilder. Knows how build. Client code calls directly
Builder Interface that defines the steps in creating product.
ConcreteBuilder Provides an implementation interface defined by the builder.  This class can be multiple depending on how many builders will be created. This is where the logic is found.
Product This is what is being build. Its not a different type, but holds different data. It defines that data to be used by the builder pattern.

Sample Code and Implementation

Let's reinforce this with a real world example using House Builder that involves the participants. Let's get started.

Download Source Code


The Project Structure



UML Class Diagram


Mapping
Design Pattern House Builder Application
Director HouseCreator
Builder IHouseBuilder
ConcreteBuilder CountryHomeBuilders, DreamBuilers
Product House

The Codes

The Interface
IHouseBuilder.cs
using BuilderDesignPattern.Product;
namespace BuilderDesignPattern.Interface
{
//Inteface that defines the steps in building house product
public interface IHouseBuilder
{
void BuildHouseFoundation();
void BuildFrames();
void BuildFloor();
void BuildRoof();
void BuildWalls();
void BuildEssentials();
void BuildFinishing();
House GetHouse();
}
}

The Product
House.cs
using System;
using System.Collections.Generic;
namespace BuilderDesignPattern.Product
{
//The product that contains data
public class House
{
public string Model { get; set; }
public string FoundationType { get; set; }
public string FloorType { get; set; }
public string Frames { get; set; }
public string RoofType { get; set; }
public string WallType { get; set; }
public List<string> Essentials { get; set; }
public List<string> Finishings { get; set; }
public House()
{
Essentials = new List<string>();
Finishings = new List<string>();
}
public void ShowData()
{
Console.WriteLine(String.Format("Model :{0}", Model));
Console.WriteLine(String.Format("Foundation :{0}", FoundationType));
Console.WriteLine(string.Format("Floor Type :{0}", FloorType));
Console.WriteLine(string.Format("Frames Type:{0}", Frames));
Console.WriteLine(string.Format("Roof Type :{0}", RoofType));
Console.WriteLine(string.Format("Wall Type :{0}", WallType));
Console.WriteLine(string.Format("Essentials :"));
foreach (var Essential in Essentials)
{
Console.WriteLine(string.Format(" {0}", Essential));
}
Console.WriteLine(string.Format("Finishing :"));
foreach (var Finishing in Finishings)
{
Console.WriteLine(string.Format(" {0}", Finishing));
}
}
}
}

The ConcreteBuilders
CountryHomeBuilders.cs
using BuilderDesignPattern.Interface;
using BuilderDesignPattern.Product;
namespace BuilderDesignPattern.Builder
{
public class CountryHomeBuilders : IHouseBuilder
{
House HouseData = new House();
public CountryHomeBuilders()
{
HouseData.Model = "Country Home";
}
public void BuildHouseFoundation()
{
HouseData.FoundationType = "Poured Concrete";
}
public void BuildFrames()
{
HouseData.Frames = "Wood";
}
public void BuildFloor()
{
HouseData.FloorType = "Wood";
}
public void BuildRoof()
{
HouseData.RoofType = "Wood Shingles";
}
public void BuildWalls()
{
HouseData.WallType = "Wood";
}
public void BuildEssentials()
{
HouseData.Essentials.Add("2 Bedrooms");
HouseData.Essentials.Add("1 Bathroom");
HouseData.Essentials.Add("1 Comfort Room");
HouseData.Essentials.Add("Living Room");
HouseData.Essentials.Add("Kitchen");
}
public void BuildFinishing()
{
HouseData.Finishings.Add("Natural Roof Painting");
HouseData.Finishings.Add("Wood Interior Paint");
}
public House GetHouse()
{
return HouseData;
}
}
}

DreamBuilders.cs
using BuilderDesignPattern.Interface;
using BuilderDesignPattern.Product;
namespace BuilderDesignPattern.Builder
{
public class DreamBuilders : IHouseBuilder
{
House HouseData = new House();
public DreamBuilders()
{
HouseData.Model = "Alexandria";
}
public void BuildHouseFoundation()
{
HouseData.FoundationType = "Poured Concrete";
}
public void BuildFrames()
{
HouseData.Frames = "Concrete";
}
public void BuildFloor()
{
HouseData.FloorType = "Concrete";
}
public void BuildRoof()
{
HouseData.RoofType = "Mansard Roof";
}
public void BuildWalls()
{
HouseData.WallType = "Bricks";
}
public void BuildEssentials()
{
HouseData.Essentials.Add("3 Bedrooms");
HouseData.Essentials.Add("1 Bathroom");
HouseData.Essentials.Add("1 Comfort Room");
HouseData.Essentials.Add("Living Room");
HouseData.Essentials.Add("Kitchen");
}
public void BuildFinishing()
{
HouseData.Finishings.Add("Maroon Roof Painting");
HouseData.Finishings.Add("Sky blue Interior Paint");
}
public House GetHouse()
{
return HouseData;
}
}
}
The Director
HouseCreator.cs
using BuilderDesignPattern.Interface;
using BuilderDesignPattern.Product;
namespace BuilderDesignPattern.Director
{
public class HouseCreator
{
IHouseBuilder HouseBuilder;
public HouseCreator(IHouseBuilder _HouseBuilder)
{
HouseBuilder = _HouseBuilder;
}
public void CreateHouse()
{
HouseBuilder.BuildHouseFoundation();
HouseBuilder.BuildFrames();
HouseBuilder.BuildFloor();
HouseBuilder.BuildRoof();
HouseBuilder.BuildWalls();
HouseBuilder.BuildEssentials();
HouseBuilder.BuildFinishing();
}
public House GetHouse()
{
return HouseBuilder.GetHouse();
}
}
}

The Client
Program.cs
using BuilderDesignPattern.Builder;
using BuilderDesignPattern.Director;
using System;
namespace BuilderDesignPattern
{
class Program
{
static void Main(string[] args)
{
HouseCreator HouseCreator1 = new HouseCreator(new DreamBuilders());
HouseCreator1.CreateHouse();
var DreamHouse = HouseCreator1.GetHouse();
DreamHouse.ShowData();
Console.WriteLine("");
Console.WriteLine("");
HouseCreator HouseCreator2 = new HouseCreator(new CountryHomeBuilders());
HouseCreator2.CreateHouse();
var CountryHome = HouseCreator2.GetHouse();
CountryHome.ShowData();
Console.ReadKey();
}
}
}

The Output


Hope this article helpful. Please drop some feedbacks!