您的位置:首页 > 其它

读书笔记6:工厂方法模式

2015-07-30 12:52 369 查看
1、概念

定义一个用于创建对象的接口,让子类决定实例化哪一个类。工厂方法是一个类的实例化延伸到子类。

2、背景

已经知道工厂模式,有一个父类SuperClass,以及这个父类的不同实现方法和算法的若干个子类ClassA,ClassB... ...,有一个工厂类DAOFactory,根据客户端传来的标识决定调用哪个子类。如下:

[csharp] view
plaincopyprint?

using System;

using System.Collections.Generic;

using System.Text;

namespace FactoryPattern

{

public abstract class SuperClass

{

public abstract void GetResult();

}

public class ClassA:SuperClass

{

public override void GetResult()

{

Console.WriteLine("A类对GetResult()的实现。");

}

}

public class ClassB : SuperClass

{

public override void GetResult()

{

Console.WriteLine("B类对GetResult()的实现。");

}

}

public class DAOFactory

{

static SuperClass super;

public static SuperClass CreateSuperClass(string type)

{

switch (type)

{

case "A":

super = new ClassA();

break;

case "B":

super = new ClassB();

break;

default:

break;

}

return super;

}

}

}

客户端

[csharp] view
plaincopyprint?

using System;

using System.Collections.Generic;

using System.Text;

namespace FactoryPattern

{

class Program

{

static void Main(string[] args)

{

SuperClass sup;

sup = DAOFactory.CreateSuperClass("A");

sup.GetResult();

sup = DAOFactory.CreateSuperClass("B");

sup.GetResult();

Console.ReadLine();

}

}

}

结果



可以看出,简单工厂模式是把到底实例化哪个类的逻辑放在工厂里判断,客户端不需要知道调用的哪个类,只关心结果就可以了。但是这里有一个问题,如果需求有了变化。那么就要增加新的类ClassC,ClassD… … 增加类不影响程序是可行的,但工厂类中的switch分支要不断地加,也就是要不断修改DAOFactory类,不符合开放封闭原则(程序实体可以扩展,但不被修改)。那么如何解决?

3、工厂方法模式

根据问题,可以有这样的方案,类ClassC,ClassD照常增加,但是需要修改工厂类。

[csharp] view
plaincopyprint?

using System;

using System.Collections.Generic;

using System.Text;

namespace FactoryPattern

{

public abstract class SuperClass

{

public abstract void GetResult();

}

public class ClassA:SuperClass

{

public override void GetResult()

{

Console.WriteLine("A类对GetResult()的实现。");

}

}

public class ClassB : SuperClass

{

public override void GetResult()

{

Console.WriteLine("B类对GetResult()的实现。");

}

}

public class ClassC : SuperClass

{

public override void GetResult()

{

Console.WriteLine("C类对GetResult()的实现。");

}

}

public class ClassD : SuperClass

{

public override void GetResult()

{

Console.WriteLine("D类对GetResult()的实现。");

}

}

public interface IFactory

{

SuperClass CreateSuperClass();

}

public class AFactory : IFactory

{

public SuperClass CreateSuperClass()

{

return new ClassA();

}

}

public class BFactory : IFactory

{

public SuperClass CreateSuperClass()

{

return new ClassB();

}

}

public class CFactory : IFactory

{

public SuperClass CreateSuperClass()

{

return new ClassC();

}

}

public class DFactory : IFactory

{

public SuperClass CreateSuperClass()

{

return new ClassD();

}

}

}

客户端

[csharp] view
plaincopyprint?

using System;

using System.Collections.Generic;

using System.Text;

namespace FactoryPattern

{

class Program

{

static void Main(string[] args)

{

IFactory factory;

SuperClass sup;

factory = new CFactory();

sup = factory.CreateSuperClass();

sup.GetResult();

factory = new DFactory();

sup = factory.CreateSuperClass();

sup.GetResult();

Console.ReadLine();

}

}

}

结果



这样,解决了修改分支的问题。但是把选择交给了客户端,需要客户端自己判断到底需要调用哪个类实现,如果需求变化客户端就需要修改。事物都是具有两面性的,因此到底使用哪种模式还需要在程序中视情况而定。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: