Factory Pattern Tutorial
Introduction
The Factory Pattern is one of the creational design patterns in object-oriented programming. It provides a way to create objects without specifying the exact class of object that will be created. The Factory Pattern defines an interface for creating an object, but allows subclasses to alter the type of objects that will be created.
Why Use the Factory Pattern?
The Factory Pattern is useful in situations where:
- The exact type of object to be created isn't known until runtime.
- A class wants its subclasses to specify the type of object to create.
- Creating an object directly within the class is not possible or practical.
Key Concepts
The key components of the Factory Pattern are:
- Product: The type of object that the factory creates.
- ConcreteProduct: A specific implementation of the Product interface.
- Creator: The interface or abstract class that declares the factory method.
- ConcreteCreator: A class that implements the Creator interface and overrides the factory method to return an instance of a ConcreteProduct.
Example in C#
Let's consider an example of a factory pattern that creates different types of "CreditCard" objects.
Step 1: Define the Product interface.
public interface ICreditCard { string GetCardType(); int GetCreditLimit(); int GetAnnualCharge(); }
Step 2: Create ConcreteProduct classes that implement the Product interface.
public class PlatinumCreditCard : ICreditCard { public string GetCardType() => "Platinum"; public int GetCreditLimit() => 35000; public int GetAnnualCharge() => 2000; } public class GoldCreditCard : ICreditCard { public string GetCardType() => "Gold"; public int GetCreditLimit() => 25000; public int GetAnnualCharge() => 1500; } public class SilverCreditCard : ICreditCard { public string GetCardType() => "Silver"; public int GetCreditLimit() => 15000; public int GetAnnualCharge() => 1000; }
Step 3: Create the Creator abstract class with the factory method.
public abstract class CreditCardFactory { public abstract ICreditCard MakeProduct(); }
Step 4: Create ConcreteCreator classes that implement the factory method.
public class PlatinumFactory : CreditCardFactory { public override ICreditCard MakeProduct() => new PlatinumCreditCard(); } public class GoldFactory : CreditCardFactory { public override ICreditCard MakeProduct() => new GoldCreditCard(); } public class SilverFactory : CreditCardFactory { public override ICreditCard MakeProduct() => new SilverCreditCard(); }
Step 5: Use the Factory to create objects.
class Program { static void Main(string[] args) { CreditCardFactory factory = null; Console.WriteLine("Enter the card type you would like to get (Platinum/Gold/Silver):"); string cardType = Console.ReadLine(); switch (cardType.ToLower()) { case "platinum": factory = new PlatinumFactory(); break; case "gold": factory = new GoldFactory(); break; case "silver": factory = new SilverFactory(); break; default: Console.WriteLine("Invalid card type."); return; } ICreditCard card = factory.MakeProduct(); Console.WriteLine("Card Type: " + card.GetCardType()); Console.WriteLine("Credit Limit: " + card.GetCreditLimit()); Console.WriteLine("Annual Charge: " + card.GetAnnualCharge()); } }
Conclusion
The Factory Pattern is a powerful technique for decoupling the creation of objects from the instances that use them. By using the Factory Pattern, you can make your code more flexible and easier to maintain. This pattern is particularly useful when the exact type of object to be created isn't known until runtime or when the creation process involves some complex logic that you want to encapsulate within a dedicated class.