Abstract Factory(C#)
阿新 • • 發佈:2018-12-18
Definition
Provide an interface for creating families of related or dependent objects without specifying their concrete classes.
Participants
The classes and/or objects participating in this pattern are:
- AbstractFactory (ContinentFactory)
- Declares an interface for operations that create abstract products
- ConcreteFactory
- Implements the operations to create concrete product objects
- AbstractProduct (Herbivore, Carnivore)
- Declares an interface for a type of product object
- Product (Wildebeest, Lion, Bison, Wolf)
- Defines a product object to be created by the corresponding concrete factory
- Implements the AbstractProduct interface
- Client (AnimalWorld)
- Uses interfaces declared by AbstractFactory and AbstractProduct classes
Sample Code in C#
This structural code demonstrates the Abstract Factory pattern creating parallel hierarchies of objects. Object creation has been abstracted and there is no need for hard-coded class names in the client code.
// --------------------------------------------------------------------------------------------------------------------// <copyright company="Chimomo's Company" file="Program.cs">// Respect the work.// </copyright>// <summary>// Structural Abstract Factory Design Pattern.// </summary>// --------------------------------------------------------------------------------------------------------------------namespace CSharpLearning{ using System; /// <summary> /// Startup class for Structural Abstract Factory Design Pattern. /// </summary> internal static class MainApp { #region Public Methods and Operators /// <summary> /// Entry point into console application. /// </summary> public static void Main() { // Abstract factory #1 AbstractFactory factory1 = new ConcreteFactory1(); var client1 = new Client(factory1); client1.Run(); // Abstract factory #2 AbstractFactory factory2 = new ConcreteFactory2(); var client2 = new Client(factory2); client2.Run(); } #endregion } /// <summary> /// The 'AbstractFactory' abstract class /// </summary> internal abstract class AbstractFactory { #region Public Methods and Operators /// <summary> /// The create product a. /// </summary> /// <returns> /// The <see cref="AbstractProductA"/>. /// </returns> public abstract AbstractProductA CreateProductA(); /// <summary> /// The create product b. /// </summary> /// <returns> /// The <see cref="AbstractProductB"/>. /// </returns> public abstract AbstractProductB CreateProductB(); #endregion } /// <summary> /// The 'ConcreteFactory1' class /// </summary> internal class ConcreteFactory1 : AbstractFactory { #region Public Methods and Operators /// <summary> /// The create product a. /// </summary> /// <returns> /// The <see cref="AbstractProductA"/>. /// </returns> public override AbstractProductA CreateProductA() { return new ProductA1(); } /// <summary> /// The create product b. /// </summary> /// <returns> /// The <see cref="AbstractProductB"/>. /// </returns> public override AbstractProductB CreateProductB() { return new ProductB1(); } #endregion } /// <summary> /// The 'ConcreteFactory2' class /// </summary> internal class ConcreteFactory2 : AbstractFactory { #region Public Methods and Operators /// <summary> /// The create product a. /// </summary> /// <returns> /// The <see cref="AbstractProductA"/>. /// </returns> public override AbstractProductA CreateProductA() { return new ProductA2(); } /// <summary> /// The create product b. /// </summary> /// <returns> /// The <see cref="AbstractProductB"/>. /// </returns> public override AbstractProductB CreateProductB() { return new ProductB2(); } #endregion } /// <summary> /// The 'AbstractProductA' abstract class /// </summary> internal abstract class AbstractProductA { } /// <summary> /// The 'AbstractProductB' abstract class /// </summary> internal abstract class AbstractProductB { #region Public Methods and Operators /// <summary> /// The interact. /// </summary> /// <param name="a"> /// The a. /// </param> public abstract void Interact(AbstractProductA a); #endregion } /// <summary> /// The 'ProductA1' class /// </summary> internal class ProductA1 : AbstractProductA { } /// <summary> /// The 'ProductB1' class /// </summary> internal class ProductB1 : AbstractProductB { #region Public Methods and Operators /// <summary> /// The interact. /// </summary> /// <param name="a"> /// The a. /// </param> public override void Interact(AbstractProductA a) { Console.WriteLine(this.GetType().Name + " interacts with " + a.GetType().Name); } #endregion } /// <summary> /// The 'ProductA2' class /// </summary> internal class ProductA2 : AbstractProductA { } /// <summary> /// The 'ProductB2' class /// </summary> internal class ProductB2 : AbstractProductB { #region Public Methods and Operators /// <summary> /// The interact. /// </summary> /// <param name="a"> /// The a. /// </param> public override void Interact(AbstractProductA a) { Console.WriteLine(this.GetType().Name + " interacts with " + a.GetType().Name); } #endregion } /// <summary> /// The 'Client' class. Interaction environment for the products. /// </summary> internal class Client { #region Fields /// <summary> /// The abstract product a. /// </summary> private AbstractProductA abstractProductA; /// <summary> /// The abstract product b. /// </summary> private AbstractProductB abstractProductB; #endregion // Constructor #region Constructors and Destructors /// <summary> /// Initializes a new instance of the <see cref="Client"/> class. /// </summary> /// <param name="factory"> /// The factory. /// </param> public Client(AbstractFactory factory) { this.abstractProductA = factory.CreateProductA(); this.abstractProductB = factory.CreateProductB(); } #endregion #region Public Methods and Operators /// <summary> /// The run. /// </summary> public void Run() { this.abstractProductB.Interact(this.abstractProductA); } #endregion }}// Output:/*ProductB1 interacts with ProductA1ProductB2 interacts with ProductA2*/
This real-world code demonstrates the creation of different animal worlds for a computer game using different factories. Although the animals created by the Continent factories are different, the interactions among the animals remain the same.
// --------------------------------------------------------------------------------------------------------------------// <copyright company="Chimomo's Company" file="Program.cs">// Respect the work.// </copyright>// <summary>// Real-World Abstract Factory Design Pattern.// </summary>// --------------------------------------------------------------------------------------------------------------------namespace CSharpLearning{ using System; /// <summary> /// Startup class for Real-World Abstract Factory Design Pattern. /// </summary> internal static class MainApp { #region Public Methods and Operators /// <summary> /// Entry point into console application. /// </summary> public static void Main() { // Create and run the African animal world ContinentFactory africa = new AfricaFactory(); var world = new AnimalWorld(africa); world.RunFoodChain(); // Create and run the American animal world ContinentFactory america = new AmericaFactory(); world = new AnimalWorld(america); world.RunFoodChain(); } #endregion } /// <summary> /// The 'AbstractFactory' abstract class /// </summary> internal abstract class ContinentFactory { #region Public Methods and Operators /// <summary> /// The create carnivore. /// </summary> /// <returns> /// The <see cref="Carnivore"/>. /// </returns> public abstract Carnivore CreateCarnivore(); /// <summary> /// The create herbivore. /// </summary> /// <returns> /// The <see cref="Herbivore"/>. /// </returns> public abstract Herbivore CreateHerbivore(); #endregion } /// <summary> /// The 'ConcreteFactory1' class /// </summary> internal class AfricaFactory : ContinentFactory { #region Public Methods and Operators /// <summary> /// The create carnivore. /// </summary> /// <returns> /// The <see cref="Carnivore"/>. /// </returns> public override Carnivore CreateCarnivore() { return new Lion(); } /// <summary> /// The create herbivore. /// </summary> /// <returns> /// The <see cref="Herbivore"/>. /// </returns> public override Herbivore CreateHerbivore() { return new Wildebeest(); } #endregion } /// <summary> /// The 'ConcreteFactory2' class /// </summary> internal class AmericaFactory : ContinentFactory { #region Public Methods and Operators /// <summary> /// The create carnivore. /// </summary> /// <returns> /// The <see cref="Carnivore"/>. /// </returns> public override Carnivore CreateCarnivore() { return new Wolf(); } /// <summary> /// The create herbivore. /// </summary> /// <returns> /// The <see cref="Herbivore"/>. /// </returns> public override Herbivore CreateHerbivore() { return new Bison(); } #endregion } /// <summary> /// The 'AbstractProductA' abstract class /// </summary> internal abstract class Herbivore { } /// <summary> /// The 'AbstractProductB' abstract class /// </summary> internal abstract class Carnivore { #region Public Methods and Operators /// <summary> /// The eat. /// </summary> /// <param name="h"> /// The h. /// </param> public abstract void Eat(Herbivore h); #endregion } /// <summary> /// The 'ProductA1' class /// </summary> internal class Wildebeest : Herbivore { } /// <summary> /// The 'ProductB1' class /// </summary> internal class Lion : Carnivore { #region Public Methods and Operators /// <summary> /// The eat. /// </summary> /// <param name="h"> /// The h. /// </param> public override void Eat(Herbivore h) { // Eat Wildebeest Console.WriteLine(this.GetType().Name + " eats " + h.GetType().Name); } #endregion } /// <summary> /// The 'ProductA2' class /// </summary> internal class Bison : Herbivore { } /// <summary> /// The 'ProductB2' class /// </summary> internal class Wolf : Carnivore { #region Public Methods and Operators /// <summary> /// The eat. /// </summary> /// <param name="h"> /// The h. /// </param> public override void Eat(Herbivore h) { // Eat Bison Console.WriteLine(this.GetType().Name + " eats " + h.GetType().Name); } #endregion } /// <summary> /// The 'Client' class /// </summary> internal class AnimalWorld { #region Fields /// <summary> /// The carnivore. /// </summary> private Carnivore carnivore; /// <summary> /// The herbivore. /// </summary> private Herbivore herbivore; #endregion // Constructor #region Constructors and Destructors /// <summary> /// Initializes a new instance of the <see cref="AnimalWorld"/> class. /// </summary> /// <param name="factory"> /// The factory. /// </param> public AnimalWorld(ContinentFactory factory) { this.carnivore = factory.CreateCarnivore(); this.herbivore = factory.CreateHerbivore(); } #endregion #region Public Methods and Operators /// <summary> /// The run food chain. /// </summary> public void RunFoodChain() { this.carnivore.Eat(this.herbivore); } #endregion }}// Output:/*Lion eats WildebeestWolf eats Bison*/