Tuesday, February 18, 2014

Common Design Patterns in C# 4.0- Factory Method


Hello again ,
Last time we discussed about Abstract Factory Pattern.
Today we will learn about the Factory Pattern.

I got this article at CodePlex 

Pattern Name:
Factory Method
Short Description: 
Create instances of derived classes
Usage:
Frequently used, fairly easy to implement and useful for centralizing object lifetime management and avoiding object creation code duplication
Complexity:
1 / 5
UML Class Diagram:
image
Explanation:
  • The abstract creator implements a factory method that returns an objects. It also contains a method for testing purposes that serves to validate the design.
  • Each concrete creator overrides the abstract factory method and returns a specific object concerning on the context.
  • In this example the factory method is used internally to set a property but it could also be used in an external context for creating objects when needed.
    public abstract class BookReader
    {
        public BookReader()
        {
            Book = BuyBook();
        }

        public Book Book { get; set; }

        public abstract Book BuyBook();

       
        public void DisplayOwnedBooks()
        {
            Console.WriteLine(Book.GetType().ToString());
        }
    }

    public class HorrorBookReader : BookReader
    {
        public override Book BuyBook()
        {
            return new Dracula();
        }
    }

    public class FantasyBookReader : BookReader
    {
        public override Book BuyBook()
        {
            return new LordOfTheRings();
        }
    }

    public class AdventureBookReader : BookReader
    {
        public override Book BuyBook()
        {
            return new TreasureIsland();
        }
    }
  • The abstract class defines the interface and class structure for all objects that get build by the specific concrete creators via their factory methods.
    public abstract class Book
    {
    }

    public class Dracula : Book
    {
    }

    public class LordOfTheRings : Book
    {
    }

    public class TreasureIsland : Book
    {
    }

    public class Encyclopedia : Book
    {
    }
  • There is also the possibility to create a C# specific solution that uses generics which also results in a valid factory method.
    public Book BuyBook<T>()
        where T : Book, new()
    {
        return new T();
    }
  • In the last step we add some code to test the software design and the Factory Method implementation in the language agnostic and in the C# specific versions.
    private static void FactoryMethod()
    {
        var bookReaderList = new List<BookReader>();

        bookReaderList.Add(new AdventureBookReader());
        bookReaderList.Add(new FantasyBookReader());
        bookReaderList.Add(new HorrorBookReader());

        foreach (var reader in bookReaderList)
        {
            Console.WriteLine(reader.GetType() .ToString());
            // language agnostic solution
            reader.DisplayOwnedBooks();

            Console.WriteLine();
        }

        // C# specific solution using generics
        var genericReader = new AdventureBookReader();
        Book book = genericReader.BuyBook<Encyclopedia>();
        Console.WriteLine(book.GetType().ToString());

        Console.ReadKey();
    }
  • When running the example you can see that everything is working as expected and that the correct classes are instantiated during runtime.
image


No comments:

Post a Comment