zoukankan      html  css  js  c++  java
  • 运用工厂模式

         工厂模式可能是我们最常遇见和使用的设计模式, 如果把工厂模式以及其实现部分看成是一个黑盒子,那么我们只需要告诉它我所需要的对象(注意:我不知道这个对象是如何实现的), 我们即可得到该对象.

    工厂模式可以细分为三种, 即: 简单工厂模式, 工厂方法模式, 虚拟工厂模式.

    简单工厂模式(Simple Factory Pattern):


    如图所示,简单工厂达到了将类的实例化封装的效果.  因为对同类class的解藕, 黑盒子外面我们能看到的ClassFactory和BaseClass借口. 把代码:
         SubClassA aEntity=new SubClassA();
         SubClassB bEntity=new SubClassB();
    转换成了:
         BaseClass xEntity=ClassFactory.Create(A);
         BaseClass xEntity=ClassFactory.Create(B);

    这样,我们可以通过统一的方法调用来实现不同的功能.

         xEntity.DoSomeThing();

    在我们只知道前提为A的情况下它调用了
         SubClassA.DoSomeThing();

    而在只知道前提为B的情况下调用:
         SubClassB.DoSomeThing();

    于是在黑盒子外的我们,只需要考虑A和B的不同情况,而不需要想A情况会怎么样,B情况如何操作了.

    工厂方法模式(Factory Method Pattern)

     

     留意工厂方法模式的类结构图,它和上面的简单工厂模式有什么样的区别?

        单看ClassFactoryA和ClassFactoryB,它们实际上就是两个简单工厂模式.因为ClassFactoryA和ClassFactoryB都是实现了BaseClass的创建过程,  所以它们是对同类对象的创建工厂.  于是提取出ClassFactoryA和ClassFactoryB的共性,  将它们归类到BaseClassFactory接口,   就实现了工厂方法模式.

     看一个工厂方法模式的例子:

    Code

    在工厂方法模式中, 具体功能的实现依然是在其所包含的两个简单工厂的结构中, 不同的是对于前文所示的A,B两种条件,工厂方法做了更细的细分.c#中datacommand就是使用的工厂方法模式. datacommand中细分为SqlDataCommand, OledbDataCommand等, 它们都是实现了DataCommand接口的具体的工厂, 同时在这两个工厂中, 我们可以选择CommandType为Queue或者SavedProcedure. 这便是在工厂中选择创建那种对象的条件A和B. 这样,我们就可以通过
    工厂方法模式创建适用于何种数据库,何种查询方式的command对象.

    虚构工厂模式(Abstract Factory Pattern)

         虚构工厂模式较以上两种模式更佳复杂,  它将不同系列, 却以不同方式完成类似功能的类别进行系列的划分.如下图所示.

     

                                              Abstruct Factory

    BaseClass1, BaseClass2和BaseClass3是互相联系的类别,它们的共同作用能完成一定功能的任务, 因为环境条件的不同,我们需要在这3个类中继承出不同的类别系列来完成任务,而这些系列被归纳到ClassFactoryA和ClassFactoryB.因为ClassFactoryA和ClassFactoryB完成的功能类似,所以我们定义了BaseClassFactory父类, 同时将这些共同的功能封装在其中.这样就形成了虚拟工厂模式. 程序示例如下:

    Code


    从结构图你也许会觉得虚拟工厂模式和工厂方法模式区别不大,只是虚拟工厂模式中同时实现了多个BaseClass的方法而已. 其实不然, 结构图的区别说明的是虚拟工厂模式强调的是系列与系列间的解藕, 而工厂方法的维度更细微一些. 同时它们在实现的方法上也不同.

    工厂方法模式将实例化推迟到子类, 在黑盒子外面我们仍将具体的class视为操作的主体, 这样我们只要通过派生出不同的工厂类继承工厂的接口,而派生于BaseClass的子类我们有足够的灵活度来重写它的实现.

         foreach (Page page in document.Pages)
            {
              Console.WriteLine(
    " " + page.GetType().Name);
            }

    虚拟工厂模式中, 工厂接口使用虚拟工厂将其子工厂的功能进行了归纳总结,它使得我们在实现虚拟工厂的时候子结构更严禁稳定.

         ContinentFactory africa = new AfricaFactory();
          AnimalWorld world 
    = new AnimalWorld(africa);
          world.RunFoodChain();


    注意比较在工厂方法模式中我们使用的Page和在虚拟工厂中使用的World之间的区别.

    只有清楚了解才能妥善使用,只有通过使用才能更加了解. 这是我对工厂模式的理解, 欢迎大家共同交流, 不怕挨砖头.

  • 相关阅读:
    请简单介绍spring支持的常用数据库事务传播属性和事务隔离级别
    Spring Bean的作用域
    成员变量与局部变量的区别
    递归与迭代
    方法参数的传递机制 ---- 值传递
    windows phone 动画 当子控件超出父控件返回时
    把dataset 输出到 excel
    代码段
    c++ 学习纪录
    做自己的代码生成器
  • 原文地址:https://www.cnblogs.com/sleeper520/p/1325549.html
Copyright © 2011-2022 走看看