Pages

Saturday, April 6, 2013

Factory Design Pattern C# Example

Factory it's such a Design Pattern which defines an interface for creating an object, but lets the classes that implement the interface decide which class to instantiate. Factory Pattern lets a class postpone instantiation to sub-classes.

Let's see Factory Pattern in action on a simple example. Assume you have two different classes Toyota and Suzuki, they both implements abstract class Car. You need to instantiate one of these classes, but you don't know which of them, it depends on user. This is perfect scenario for the Factory Pattern.

Factory Design Pattern example program diagram


So here are our two main classes and the interface (abstract class):
abstract class Car
{
    public abstract string Company { get; }
    public abstract string Model { get; set; }
    public abstract int Speed { get; set; }
}

class Suzuki : Car
{
    private readonly string _company;
    private string _model;
    private int _speed;

    public Suzuki(string model, int speed)
    {
        _company = "Suzuki";
        _model = model;
        _speed = speed;
    }

    public override string Company
    {
        get { return _company; }
    }

    public override string Model
    {
        get { return _model; }
        set { _model = value; }
    }

    public override int Speed
    {
        get { return _speed; }
        set { _speed = value; }
    }
}

class Toyota : Car
{
    private readonly string _company;
    private string _model;
    private int _speed;

    public Toyota(string model, int speed)
    {
        _company = "Toyota";
        _model = model;
        _speed = speed;
    }

    public override string Company
    {
        get { return _company; }
    }

    public override string Model
    {
        get { return _model; }
        set { _model = value; }
    }

    public override int Speed
    {
        get { return _speed; }
        set { _speed = value; }
    }
}
Abstract CarFactory class is an interface for our ToyotaFactory and SuzukiFactory classes that will be responsible for the instantiation of corresponding car, therefore they only have one single GetCar() method.
abstract class CarFactory
{
    public abstract Car GetCar();
}

class ToyotaFactory : CarFactory
{
    private string _model;
    private int _speed;

    public ToyotaFactory(string model, int speed)
    {
        _model = model;
        _speed = speed;
    }
    public override Car GetCar()
    {
        return new Toyota(_model, _speed);
    }
}

class SuzukiFactory: CarFactory
{
    private string _model;
    private int _speed;

    public SuzukiFactory(string model, int speed)
    {
        _model = model;
        _speed = speed;
    }

    public override Car GetCar()
    {
        return new Suzuki(_model, _speed);
    }
}
What is left is only CarAssembler class which will create needed type of car depending on the factory that it receives as parameter.
class CarAssembler
{
    public void AssembleCar(CarFactory factory)
    {
        Car car = factory.GetCar();
        Console.WriteLine("{0} {1} assembled successfully. Maximum speed is {2} mph", 
            car.Company, car.Model, car.Speed);
    }
}
That's all! Now you can instantiate corresponding car object depending on user input:
static void Main(string[] args)
{
    CarFactory factory = null;
    Console.WriteLine("Which car you would like to build?");
    string car = Console.ReadLine();
    if (car == "toyota")
        factory = new ToyotaFactory("Corolla", 130);
    else
        factory = new SuzukiFactory("Swift", 110);

    new CarAssembler().AssembleCar(factory);
}
Here is the program output:

Factory Pattern example output

Download the source code (Visual Studio 2012 project).

13 comments:

  1. whats difference between factory and abstract Factory Pattern .

    ReplyDelete
  2. With the Factory pattern, you produce implementations (Apple, Banana, Cherry, etc.) of a particular interface let's say, IFruit.

    With the Abstract Factory pattern, you produce implementations of a particular Factory interface, let's say IFruitFactory. Each of those knows how to create different kinds of fruit.

    ReplyDelete
  3. That's a nice article and all, but you defeat the purpose of a pattern.
    Take out all the COMPANY references... add... Here...

    Car.cs
    namespace Patterns
    {
    abstract class Car
    {
    public abstract string Make { get; set; }
    public abstract string Model { get; set; }
    public abstract int Speed { get; set; }
    }
    }

    Delete SusukiFactory.cs
    Delete Susuki.cs


    Toyota.cs
    namespace Patterns
    {
    class Toyota : Car
    {
    private string _make;
    private string _model;
    private int _speed;

    public Toyota(string make, string model, int speed)
    {

    _make = make;
    _model = model;
    _speed = speed;
    }

    public override string Make
    {
    get { return _make; }
    set { _make = value; }
    }

    public override string Model
    {
    get { return _model; }
    set { _model = value; }
    }

    public override int Speed
    {
    get { return _speed; }
    set { _speed = value; }
    }

    }
    }



    CarFactory.cs
    namespace Patterns
    {
    abstract class CarFactory
    {
    public abstract Car GetCar();
    }
    }



    ToyotaFactory.cs

    namespace Patterns
    {

    class ToyotaFactory : CarFactory
    {
    private string _make;
    private string _model;
    private int _speed;

    public ToyotaFactory(string make, string model, int speed)
    {
    _make = make;
    _model = model;
    _speed = speed;
    }
    public override Car GetCar()
    {
    return new Toyota( _make, _model, _speed);
    }
    }

    }



    CarAssembler.cs

    using System;

    namespace Patterns
    {
    class CarAssembler
    {
    public void AssembleCar(CarFactory factory)
    {
    Car car = factory.GetCar();
    Console.WriteLine("{0} {1} assembled successfully. Maximum speed is {2} mph",
    car.Make, car.Model, car.Speed);
    Console.ReadKey();
    }
    }
    }


    Program.cs

    using System;

    namespace Patterns
    {
    class Patterns
    {
    static void Main(string[] args)
    {
    CarFactory factory = null;
    Console.WriteLine("Which car you would like to build?");
    string car = Console.ReadLine();

    switch (car)
    {
    case "Toyota":
    factory = new ToyotaFactory("Toyota", "Corolla", 130);
    break;
    case "Susuki":
    factory = new ToyotaFactory("Susuki", "Swift", 110);
    break;
    case "Chevy":
    factory = new ToyotaFactory("Chevy", "Jimmy", 95);
    break;
    case "Ford":
    factory = new ToyotaFactory("Ford", "Explorer", 85);
    break;
    default:
    factory = new ToyotaFactory("Dodge", "Ram 1500",120);
    break;
    }


    new CarAssembler().AssembleCar(factory);
    }
    }
    }


    Now everything is ran through the Toyota factory. We killed two classes. Susuki was so close to the Toyota Factory it wasn't funny. The purpose of patterns is to eliminate redundant code, not create it.

    ReplyDelete
  4. very good article.I have asked a question that why we have to use abstract method in public abstract Car GetCar(); under CarFactory class. Can we use interface.

    Thanks
    Sagar B
    sagar.biswas@gmail.com

    ReplyDelete