Design Patterns In C#: Abstract Factory

by Ron Kahr 22. April 2012 09:59

Definition
In the Abastract Factory design pattern objects are produced that follow a general pattern. At runtime this factory is paired with any concrete factory to produce objects that follow a certain pattern. In other words, the Abstract Factory is a super-factory which creates other factories (Factory of factories) .

Intent
The Abstract Factory offers the interface for creating a family of related objects, without explicitly specifying their classes.

Here is a UML diagram of the Abastract Factory pattern (click on the image to see a larger version):

The classes that participate to the Abstract Factory pattern are:

  • AbstractFactory - declares a interface for operations that create abstract products. ConcreteFactory - implements operations to create concrete products.
  • AbstractProduct - declares an interface for a type of product objects.
  • Product - defines a product to be created by the corresponding ConcreteFactory; it implements the AbstractProduct interface.
  • Client - uses the interfaces declared by the AbstractFactory and AbstractProduct classes.

Sample Code In C#

class AbstractFactoryPattern
{
    public static void AFPMain()
    {
        DepartmentFactory humanResources = new HRFactory();
        Department department = new Department(humanResources);
        department.DoPerformanceReviews();

        DepartmentFactory it = new ITFactory();
        department = new Department(it);
        department.DoPerformanceReviews();

        Console.ReadKey();
    }
}

interface IEmployee
{
    string Title { get;}
}
abstract class DepartmentFactory
{
    public abstract VicePresident CreateVicePresident();
    public abstract DepartmentManager CreateDepartmentManager();
    public abstract SectionHead CreateSectionHead();
    public abstract Worker CreateWorker();
}

class ITFactory : DepartmentFactory
{
    public override VicePresident CreateVicePresident()
    {
        return new VicePresidentOfIT();
    }

    public override DepartmentManager CreateDepartmentManager()
    {
        return new SeniorManagerOfIT();
    }

    public override SectionHead CreateSectionHead()
    {
        return new SeniorManagerOfDevelopment();
    }

    public override Worker CreateWorker()
    {
        return new ApplicationDeveloper();
    }
}

class HRFactory : DepartmentFactory
{
    public override VicePresident CreateVicePresident()
    {
        return new VicePresidentOfHR();
    }

    public override DepartmentManager CreateDepartmentManager()
    {
        return new DirectorOfHR();
    }

    public override SectionHead CreateSectionHead()
    {
        return new BenefitsSupervisor();
    }

    public override Worker CreateWorker()
    {
        return new BenefitsCoordinator();
    }
}

abstract class VicePresident : IEmployee
{
    public abstract string Title {get;}

    public abstract void Review(DepartmentManager dm);
}

abstract class DepartmentManager : IEmployee {
    public abstract string Title {get;}

    public abstract void Review(SectionHead sh);
}

abstract class SectionHead : IEmployee {
    public abstract string Title{get;}

    public abstract void Review(Worker w);
}

abstract class Worker : IEmployee {
    public abstract string Title{get;}
}

class VicePresidentOfIT : VicePresident 
{ 
    private string _title = "Vice President Of IT";

    public override string Title
    {
        get
        {
            return _title;
        }
    }

    public override void  Review(DepartmentManager dm)
    {
        Console.WriteLine(this.Title + " reviews " + dm.Title);
    }
}

class SeniorManagerOfIT : DepartmentManager 
{
    private string _title = "Senior Manager Of IT";

    public override string Title
    {
        get
        {
            return _title;
        }
    }

    public override void Review(SectionHead sh)
    {
        Console.WriteLine(this.Title + " reviews " + sh.Title);
    }
}

class SeniorManagerOfDevelopment : SectionHead {
    private string _title = "Senior Manager Of Development";

    public override string Title
    {
        get
        {
            return _title;
        }
    }

    public override void Review(Worker w)
    {
        Console.WriteLine(this.Title + " reviews " + w.Title);
    }
}

class ApplicationDeveloper : Worker {
    private string _title = "Application Developer";

    public override string Title
    {
        get
        {
            return _title;
        }
    }
}

class VicePresidentOfHR : VicePresident 
{
    private string _title = "Vice President Of HR";

    public override string Title
    {
        get
        {
            return _title;
        }
    }

    public override void Review(DepartmentManager dm)
    {
        Console.WriteLine(this.Title + " reviews " + dm.Title);
    }
}

class DirectorOfHR : DepartmentManager {
    private string _title = "Director Of HR";

    public override string Title
    {
        get
        {
            return _title;
        }
    }

    public override void Review(SectionHead sh)
    {
        Console.WriteLine(this.Title + " reviews " + sh.Title);
    }
}

class BenefitsSupervisor : SectionHead {
    private string _title = "Benefits Supervisor";

    public override string Title
    {
        get
        {
            return _title;
        }
    }

    public override void Review(Worker w)
    {
        Console.WriteLine(this.Title + " reviews " + w.Title);
    }
}

class BenefitsCoordinator : Worker {
    private string _title = "Benefits Coordinator";

    public override string Title
    {
        get
        {
            return _title;
        }
    }
}

class Department
{
    private VicePresident _vicePresident;
    private DepartmentManager _departmentManager;
    private SectionHead _sectionHead;
    private Worker _worker;

    public Department(DepartmentFactory factory)
    {
        _vicePresident = factory.CreateVicePresident();
        _departmentManager = factory.CreateDepartmentManager();
        _sectionHead = factory.CreateSectionHead();
        _worker = factory.CreateWorker();
    }

    public void DoPerformanceReviews()
    {
        _vicePresident.Review(_departmentManager);
        _departmentManager.Review(_sectionHead);
        _sectionHead.Review(_worker);
    }
}

The output from running this code is:

Vice President of HR reviews Director Of HR 
Director of HR reviews Benefits Supervisor 
Benefits Supervisor reviews Benefits Coordinator 
Vice President of IT reviews Senior Manager of IT 
Senior Manager Of IT reviews Senior Manager Of Development 
Senior Manager Of Development reviews Application Developer

Tags:

Month List

About the author

Something about the author

Page List