Builder Pattern In C#

Builder Pattern in C#.

Builder Pattern

Builder Pattern comes under creation type design pattern. It helps in separating the construction of a complex object by using step by step approach. In this, Director controls the creation process, and Builder is independent of the creation process.

The following items are elements of the builder pattern,

  • Builder - It specifies an abstract interface for creating parts of a product object.
  • ConcreteBuilder - It creates and assembles parts of the product by implanting The Builder Interface. It also provides an interface for retrieving the product.
  • Director - It constructs an object using Builder Interface. It actually acts as an overall master object that takes care of the builder creation and setup, and makes sure it has the 'ConcreteBuilders' it requires.
  • Product - The target object produced by the builder.

To understand the above point, let us take an example of laptop manufacturing system. Let's assume that we have a system installed at one of the laptop vendors. Now, the manufacturer may decide to create a laptop based on parameters like Touchscreen, Operating System, Battery and Stylus. If we have the objects for all these parts, then creation of product with any combination of above parts would lead to a very complex and unmanageable code in the client application i.e. the module that will decide what kind of laptop needs to be built.

Below is implementation, 

  1. public enum ScreenType {  
  2.     ScreenType_TOUCH_CAPACITIVE,  
  3.     ScreenType_NON_TOUCH  
  4. };  
  5. public enum Battery {  
  6.     MAH_25000,  
  7.     MAH_15000,  
  8.     MAH_20000  
  9. };  
  10. public enum OperatingSystem {  
  11.     ANDROID,  
  12.     WINDOWS,  
  13.     SYMBIAN  
  14. };  
  15. public enum Stylus {  
  16.     YES,  
  17.     NO  
  18. };   

Above are some helper enums to identify various parts.

Product 

  1. class Laptop {  
  2.     // fields to hold the part type  
  3.     string laptopName;  
  4.     ScreenType laptopScreen;  
  5.     Battery laptopBattery;  
  6.     OperatingSystem laptopOS;  
  7.     Stylus laptopStylus;  
  8.     public Laptop(string name) {  
  9.         laptopName = name;  
  10.     }  
  11.     // Public properties to access laptop parts  
  12.     public string LaptopName {  
  13.         get {  
  14.             return laptopName;  
  15.         }  
  16.     }  
  17.     public ScreenType LaptopScreen {  
  18.         get {  
  19.             return laptopScreen;  
  20.         }  
  21.         set {  
  22.             laptopScreen = value;  
  23.         }  
  24.     }  
  25.     public Battery LaptopBattery {  
  26.         get {  
  27.             return laptopBattery;  
  28.         }  
  29.         set {  
  30.             laptopBattery = value;  
  31.         }  
  32.     }  
  33.     public OperatingSystem LaptopOS {  
  34.         get {  
  35.             return laptopOS;  
  36.         }  
  37.         set {  
  38.             laptopOS = value;  
  39.         }  
  40.     }  
  41.     public Stylus LaptopStylus {  
  42.         get {  
  43.             return laptopStylus;  
  44.         }  
  45.         set {  
  46.             laptopStylus = value;  
  47.         }  
  48.     }  
  49.     // Methiod to display laptop details in our own representation  
  50.     public override string ToString() {  
  51.         return string.Format("Name: {0}\nScreen: {1}\nBattery {2}\nOS: {3}\nStylus: {4}", LaptopName, LaptopScreen, LaptopBattery, LaptopOS, LaptopStylus);  
  52.     }  
  53. }   

Shown above is example of Product class which is created for assembling the parts of Laptop.

Builder 

  1. interface ILaptopBuilder {  
  2.     void BuildScreen();  
  3.     void BuildBattery();  
  4.     void BuildOS();  
  5.     void BuildStylus();  
  6.     Laptop laptop {  
  7.         get;  
  8.     }  
  9. }   

The above Builder is providing the functions for creating each of the parts for any Laptop as ILaptopBuilder.

ConcreteBuilder 

  1. class AndroidLaptopBuilder: ILaptopBuilder {  
  2.     Laptop laptop  
  3.     public AndroidLaptopBuilder() {  
  4.         laptop = new Laptop("Android Laptop");  
  5.     }#  
  6.     region ILaptopBuilder Members  
  7.     public void BuildScreen() {  
  8.         laptop = ScreenType.ScreenType_TOUCH_RESISTIVE;  
  9.     }  
  10.     public void BuildBattery() {  
  11.         laptop.LaptopBattery = Battery.MAH_15000;  
  12.     }  
  13.     public void BuildOS() {  
  14.         laptop.LaptopOS = OperatingSystem.ANDROID;  
  15.     }  
  16.     public void BuildStylus() {  
  17.         laptop.LaptopStylus = Stylus.YES;  
  18.     }  
  19.     // GetResult Method which will return the actual Laptop  
  20.     public Laptoplaptop {  
  21.         get {  
  22.             return laptop;  
  23.         }  
  24.     }#  
  25.     endregion  
  26. }  
  27. class WindowslaptoLBuilder: ILaptopBuilder {  
  28.     Laptop laptop;  
  29.     public WindowsLaptopBuilder() {  
  30.         laptop = new WindowsLaptop("Windows Laptop");  
  31.     }#  
  32.     region ILaptopBuilder Members  
  33.     public void BuildScreen() {  
  34.         laptop.LaptopScreen = ScreenType.ScreenType_TOUCH_CAPACITIVE;  
  35.     }  
  36.     public void BuildBattery() {  
  37.         laptop.LaptopBattery = Battery.MAH_20000;  
  38.     }  
  39.     public void BuildOS() {  
  40.         laptop.LaptopOS = OperatingSystem.WINDOWS_LAPTOP;  
  41.     }  
  42.     public void BuildStylus() {  
  43.         laptop.LaptopStylus = Stylus.NO;  
  44.     }  
  45.     // GetResult Method which will return the actual laptop  
  46.     public Laptop laptop; {  
  47.         get {  
  48.             return laptop;  
  49.         }  
  50.     }#  
  51.     endregion  
  52. }   

We have implemented Concrete builder class by inheriting ILaptopBuilder for Android and Windows Laptop.

Director 

  1. class Manufacturer {  
  2.     public void Construct(ILaptopBuilder laptopBuilder) {  
  3.         laptopBuilder.BuildBattery();  
  4.         laptopBuilder.BuildOS();  
  5.         laptopBuilder.BuildScreen();  
  6.         laptopBuilder.BuildStylus();  
  7.     }  
  8. }   

In the above example, we have created a Director class that is having the Construct method accepting an ILaptopBuilder and then calling the respective functions of the ConcreteBuilders internally. 

  1. class Program {  
  2.     static void Main(string[] args) {  
  3.         // Lets create the Director first  
  4.         Manufacturer newManufacturer = new Manufacturer();  
  5.         // Lets have the Builder class ready  
  6.         ILaptopBuilder laptopBuilder = null;  
  7.         // Now let us create an android laptop  
  8.         laptopBuilder = new AndroidLaptopBuilder();  
  9.         newManufacturer.Construct(laptopBuilder);  
  10.         Console.WriteLine("A new Laptop built:\n\n{0}", laptopBuilder.Laptop.ToString());  
  11.         // Now let us create a Windows Laptop  
  12.         laptopBuilder = new WindowsLaptopBuilder();  
  13.         newManufacturer.Construct(laptopBuilder);  
  14.         Console.WriteLine("A new Laptop built:\n\n{0}", laptopBuilder.Laptop.ToString());  
  15.     }  
  16. }