設計模式-工廠方法模式(FactoryMethod)

簡介:編程

簡單工廠模式將類的示例化放在工廠對象中。ide

工廠方法模式是簡單工廠模式的延伸,不一樣的是其將子類的實例化延遲到子類工廠中實現,自己僅定義一個建立對象的接口。測試

工廠方法模式主要由四部分組成:spa

1.抽象產品(product) -同簡單工廠模式.net

是全部具體產品角色的父類,它負責描述全部實例所共有的公共接口,抽象類或者接口code

2.具體產品(Concrete Product) -同簡單工廠模式
即爲Product的實現對象,特指某一具體產品,通常有多個這樣的類。對象

3.工廠角色(Creator) -同簡單工廠模式接口

工廠基類,能夠爲接口、抽象類、實體類,聲明工廠方法,工廠方法通常爲抽象方法,返回Product對象,也能夠在工廠方法中提供默認實現,返回一個Default的Product實例對象。get

4.具體工廠角色(ConcreteCreator)產品

重寫Creator中的工廠方法,返回具體的Product實例。

具體實例:

上面簡單工廠的例子,已經很好的實現了對交易修改備案的操做。無論後續新增任何交易,稍微改下代碼便可輕鬆實現修改備案記錄。

如今客戶提到,要對系統中帳戶修改、對手修改記錄修改備案,PS:之後可能還會有其餘對象的修改備案。

代碼實現:

public abstract class DiffClass
{
    public abstract void Diff(Object aOldObject, Object aNewObject);
}

public class AccountDiff : DiffClass
{
    public override void Diff(Object aOldAccount, Object aNewAccount)
    {
        Console.WriteLine("記錄帳戶修改備案信息");
    }
}

public class PartyDiff : DiffClass
{
    public override void Diff(Object aOldParty, Object aNewParty)
    {
        Console.WriteLine("記錄交易對手修改備案信息");
    }
}

interface IFactoryMethod
{
    DiffClass CreateDiffClass();
}

public class AccountFactory : IFactoryMethod
{
    public DiffClass CreateDiffClass()
    {
        return new AccountDiff();
    }
}

public class PartyFactory : IFactoryMethod
{
    public DiffClass CreateDiffClass()
    {
        return new PartyDiff();
    }
}

class FactoryMethodTest
{
    static void Main(String[] args)
    {
        Account oldAccount = new Account();
        Account newAccount = new Account();
        IFactoryMethod factory1 = new AccountFactory();
        factory1.CreateDiffClass().Diff(oldAccount, newAccount);

        Party oldParty = new Party();
        Party newParty = new Party();
        IFactoryMethod factory2 = new PartyFactory();
        factory2.CreateDiffClass().Diff(oldParty, newParty);
        Console.ReadLine();
    }
}
後續若是用戶提到須要記錄用戶修改備案,不用修改原始代碼,新增代碼以下便可:
public class UserDIff : DiffClass
{
    public override void Diff(object aOldUser, object aNewUser)
    {
        Console.WriteLine("記錄用戶修改備案信息");
    }
}

public class UserFactory : IFactoryMethod
{
    public DiffClass CreateDiffClass()
    {
        return new UserDIff();
    }
}

補充分析:

工廠方法模式的本質:延遲到子類來選擇實現

優勢:

a.工廠方法給子類提供了一個掛鉤,使得擴展新的對象更容易。例如上面提到的新增用戶修改備案或者後續新增其它對象的修改備案,不須要修改原有任何代碼。新增新的工廠方法和新的子類便可。

b.能夠在不知道具體實現的狀況下編程

父類的工廠模式自己通常不實例化具體產品對象,不關心細節,建立具體產品對象的任務延遲到子類中。

缺點:

工廠方法中須要建立產品對象,也就是須要選擇具體的產品對象並建立他們的實例,具體產品對象和工廠方法耦合。

跟簡單工廠模式的區別:

簡單工廠模式,直接在工廠類中選擇實現具體產品實例。

工廠方法模式,將具體產品的實例放在具體工廠裏(工廠角色的子類)。父類工廠角色裏面的工廠方法,依賴於抽象而不是具體實現,面向接口編程。

其它代碼:

簡單工廠模式自己是工廠方法模式的一種特殊狀況。其實顯示中兩種模式是能夠混和使用的。

參考代碼如:

    #region 簡單工廠
    public abstract class DiffClass
    {
        public abstract void Diff(Object aOldObject, Object aNewObject);
    }

    public class BondTradeDiff : DiffClass
    {
        public override void Diff(Object aOldTrade, Object aNewTrade)
        {
            Console.WriteLine("記錄現券交易備案!");
        }
    }

    public class FutureTradeDiff : DiffClass
    {
        public override void Diff(Object aOldTrade, Object aNewTrade)
        {
            Console.WriteLine("記錄期貨交易備案");
        }
    }

    public class FactoryMethod
    {
        public virtual DiffClass CreateDiffClass(object aObject)//參數化工廠方法
        {
            if (aObject is BondTrade)
                return new BondTradeDiff();
            else if (aObject is FutureTrade)
                return new FutureTradeDiff();
            else
                return null;
        }
    }
    #endregion

    #region 工廠方法
    public class AccountDiff : DiffClass
    {
        public override void Diff(Object aOldAccount, Object aNewAccount)
        {
            Console.WriteLine("記錄帳戶修改備案信息");
        }
    }

    public class AccountFactory : FactoryMethod
    {
        public override DiffClass CreateDiffClass(object aObject)
        {
            return new AccountDiff();
        }
    }
    #endregion

    #region 測試代碼
    public class SimpleFactoryAndFactoryMethod
    {
        static void Main(String[] args)
        {
            FactoryMethod factory = new FactoryMethod();

            //測試現券交易修改備案
            Trade oldBondTrade = new BondTrade();
            Trade newBondTrade = new BondTrade();
            factory.CreateDiffClass(newBondTrade).Diff(oldBondTrade, newBondTrade);

            //測試期貨交易修改備案
            Trade oldFutureTrade = new FutureTrade();
            Trade newFutureTrade = new FutureTrade();
            factory.CreateDiffClass(newFutureTrade).Diff(oldFutureTrade, newFutureTrade);

            //測試帳戶修改備案
            Account oldAccount = new Account();
            Account newAccount = new Account();
            FactoryMethod factory1 = new AccountFactory();
            factory1.CreateDiffClass(newAccount).Diff(oldAccount, newAccount);

            Console.ReadLine();
        }
    }
    #endregion
}
相關文章
相關標籤/搜索