[导入]Factory Method Design Pattern

Definition

Define an interface for creating an object, but let subclasses decide which class to instantiate. Factory Method lets a class defer instantiation to subclasses.
      定义一个创建对象的接口,但是让子类来决定实例化那个类。工厂方法使实例化推迟到子类。

UML Diagram

Discussion

Factory MethodTemplate Method的比较
       Factory Method is to creating objects as Template Method is to implementing an algorithm. A superclass specifies all standard and generic behavior (using pure virtual "placeholders" for creation steps), and then delegates the creation details to subclasses that are supplied by the client.

在哪些情况下没有必要使用Factory Method
       People often use Factory Method as the standard way to create objects; but it isn't necessary if: the class that's instantiated never changes, or instantiation takes place in an operation that subclasses can easily override (such as an initialization operation). [GOF, p136]

Factory Method is similar to Abstract Factory but without the emphasis on families.

       Factory Methods are routinely specified by an architectural framework, and then implemented by the user of the framework.

       在工厂模式中,有两个类体系:产品类和工厂类,它们之间往往有平行的等级结构,一一对应。

Rules of thumb

Abstract Factory classes are often implemented with Factory Methods, but they can be implemented using Prototype. [GOF, p95]

Factory Methods are usually called within Template Methods. [GOF, p116]

Factory Method: creation through inheritance. Prototype: creation through delegation.

Often, designs start out using Factory Method (less complicated, more customizable, subclasses proliferate) and evolve toward Abstract Factory, Prototype, or Builder (more flexible, more complex) as the designer discovers where more flexibility is needed. [GOF, p136]

Prototype doesn't require subclassing, but it does require an Initialize operation. Factory Method requires subclassing, but doesn't require Initialize. [GOF, p116]

一个example来说明使用factory method的好处(引用[6]

也许会有人认为,虽然通过工厂方法,将创建IShape对象的职责转交给工厂对象,然而在工厂类的结构中,仍然存在具体的工厂类对象。如此以来,虽然我们解除了模块与具体Shape对象的依赖,却增加了对具体工厂对象的依赖,这会带来何种益处?

让我们从对象创建的频率来分析。对于一个图形工具而言,IShape对象的创建无疑是频繁的,最大的可能性是在这个项目的各个模块中都可能存在创建 IShape对象的需要。而工厂对象则不尽然,我们完全可以集中在一个模块中,初始化这个工厂对象,而在需要IShape对象的时候,直接调用工厂实例的 CreateShape()就可以达到目的。

举例来说,假设在图形工具中,有三个模块:ModuleAModuleBModuleC;这三个模块中都需要创建Square对象,则按照原来的设计方案,这三个模块都包含这样一行代码:

IShape shape = new Square();

此时,与Square对象有依赖关系的就包括了ModuleAModuleBModuleC三个模块。如果我们需要修改shape对象为 Circle类型,则这个变动无疑会影响到上述的三个模块。现在,我们引入Factory Method模式,并增加一个模块名为ModuleFactory,在这个模块中,我们创建一个工厂对象:

IShapeFactory shapeFactory = new SquareFactory();

如此以来,原来的三个模块有关Square对象的创建,就相应地修改为:

IShape shape = shapeFactory.CreateShape();

此时,即使需求发生改变,需要对shape对象进行修改,那么我们只需要修改ModuleFactory模块中的代码:

IShapeFactory shapeFactory = new CircleFactory();

ModuleAModuleBModuleC三个模块则根本不需要作任何改变。如此的设计改进,虽然在项目中增加了三个工厂对象,并引入了 ModuleFactory,但它却完成了ModuleAModuleBModuleC与具体的Square对象的解耦,从而将这三个模块与产品对象的依赖性转嫁到ModuleFactory上。如此以来,牵一发而不动其全身,极大地提高了模块的重用性。

从上述的分析可知,引入工厂对象并不是简单地为产品建立相应的工厂,而是要注意划分各个模块的职责,将工厂对象的创建放到合适的地方。最佳方案莫过于将创建工厂对象的职责集中起来,放到一个模块中;而不是在需要创建产品时,才创建工厂对象。错误的例子是在创建产品时将工厂对象的创建于产品对象的创建放在一起,并分布在各个模块中:

IShapeFactory shapeFactory = new SquareFactory();

IShape shape = shapeFactory.CreateShape();

这样的做法,则引入Factory Method模式,无异于画蛇添足了。

Reference

[1]  http://www.dofactory.com/Patterns/Patterns.aspx

最简单明了地说明了factory method的基本知识

[2] http://home.earthlink.net/~huston2/dp/factoryMethod.html

有很多有用的讨论和经验规则,与其他design pattern的关系和比较

[3] http://www2.ing.puc.cl/~jnavon/IIC2142/patexamples.htm

Non-Software Examples of Software Design Patterns

[4] http://www.ondotnet.com/pub/a/dotnet/2003/08/11/factorypattern.html

This article describes some instances of a commonly occurring design pattern in the FCL: the Factory Method design pattern.  (by Amit Goel)

[5] http://msdn2.microsoft.com/en-us/library/ms954600.aspx#Mtps_DropDownFilterText

Exploring the Factory Design Pattern

[6] http://www.brucezhang.com/?p=56

[7] http://terrylee.cnblogs.com/archive/2006/01/04/310716.aspx
 

下一步学习:

(1)  [4],[6], [7]:学习Factory Method FCl里的应用,熟悉FCL里一些重要类的实现(WebRequest,IEnumerable,HttpApplicationFactory

(2) Abstract Factory 以及与Factory Method的比较。

可以在Google Image里搜索 Abstract Factory”,可以找到很多有用的文章。


    文章来源:http://abram06.blog.163.com/blog/static/721505200611632530837
    posted @ 2006-12-06 15:26  玉泉老博  阅读(316)  评论(0编辑  收藏  举报
    Free counter and web stats