设计模式之template method模式

设计模式之template method模式

算法意图:

将算法骨架定义在父类当中,具体的实现放到子类当中。Template method可以不改变算法的骨架在子类中重新定义算法中的某些特定的步骤。

算法适用性:

1.       一次性将算法的不变部分封装到父类当中,将可变的部分放到子类中去实现。

2.       各子类的公共部分亚冠提取出来放到父类当中,避免代码重复,分离变化和不变的地方。

3.       通过hook来控制子类的扩展。

4.       模板方法的格式:
class TemplateMethod_Demo
{
  public:
    <返回值类型> <模板方法名>(<参数列表>); //模板方法成员函数,定义为公有的非虚成员函数,供客户调用;
  protected:
    virtual <返回值类型> <抽象操作的方法名>(<参数列表>) = 0;//抽象操作(可选),:原语操作,用纯虚函数表示,必须被重定义,定义为保护类型的,只能被模板方法本身调用;
    virtual <返回值类型> <钩子操作的方法名>(<参数列表>){};  //钩子操作(必选),:原语操作,用虚函数表示,可被重定义,提供缺省实现,定义为保护类型的,只能被模板方法本身调用;
};

 

  1 //  template.cpp : 定义控制台应用程序的入口点。
  2 //
  3
  4 #include  " stdafx.h "
  5 #include < iostream >
  6 using   namespace  std;
  7
  8 class  AbstractClass
  9 {
 10public:
 11     AbstractClass(){}
 12     virtual ~AbstractClass(){}
 13     virtual void doFirst();
 14     virtual void doAfter();
 15     // 这个函数中定义了算法的轮廓
 16     void TemplateMethod()
 17     {
 18         doFirst();
 19         PrimitiveOperation1();
 20         PrimitiveOperation2();
 21          if (b_jugle) 
 22          {
 23              doSthElse();
 24          }
 
 25         doAfter();
 26     }

 27     virtual void setHookTrue()
 28     {
 29         AbstractClass::b_jugle = true;
 30     }
;
 31
 32protected:
 33     // 纯虚函数,由派生类实现之
 34     virtual void PrimitiveOperation1() = 0;
 35     virtual void PrimitiveOperation2() = 0;
 36     virtual void  doSthElse() = 0;
 37     static bool b_jugle;
 38     
 39     
 40}
;
 41
 42 bool  AbstractClass::b_jugle  =   false ;
 43
 44
 45 void  AbstractClass::doFirst()
 46 {
 47    cout<<"do std before"<<endl;
 48}

 49
 50 void  AbstractClass::doAfter()
 51 {
 52    cout<<"do std after"<<endl;
 53}

 54
 55 //  继承自AbstractClass,实现算法
 56 class  ConcreateClass:  public  AbstractClass
 57 {
 58public:
 59     ConcreateClass(){}
 60     virtual ~ConcreateClass(){}
 61
 62protected:
 63     virtual void PrimitiveOperation1()
 64     {
 65         cout << "PrimitiveOperation1 by ConcreateClass\n";
 66     }

 67     virtual void PrimitiveOperation2()
 68     {
 69         cout << "PrimitiveOperation2 by ConcreateClass\n";
 70     }

 71     virtual void doSthElse()
 72     {
 73         cout<<"so something else!\n"<<endl;
 74     }

 75}
;
 76
 77
 78 //  继承自AbstractClass,实现算法
 79 class  ConcreateClassNew:  public  AbstractClass
 80 {
 81public:
 82     ConcreateClassNew(){}
 83     virtual ~ConcreateClassNew(){}
 84    
 85protected:
 86     virtual void PrimitiveOperation1()
 87     {
 88         cout << "PrimitiveOperation1 by ConcreateClassNew\n";
 89     }

 90     virtual void PrimitiveOperation2()
 91     {
 92         cout << "PrimitiveOperation2 by ConcreateClassNew\n";
 93     }

 94      virtual void doSthElse()
 95     {
 96         cout<<"so something else!\n"<<endl;
 97     }

 98    
 99}
;
100
101
102 int  _tmain( int  argc, _TCHAR *  argv[])
103 {
104    AbstractClass* pConcreateClass = new ConcreateClass;
105    pConcreateClass->TemplateMethod();
106    delete pConcreateClass;
107
108
109    AbstractClass* pConcreateClass2 = new ConcreateClassNew;
110    pConcreateClass2->setHookTrue();
111    pConcreateClass2->TemplateMethod();
112    delete pConcreateClass2;
113    return 0;
114}

115
116

运行结果:


template method的设计原则:
1.封装变化部分;
2.对接口编程
3. 好莱坞原则:别调用我们,在我们需要时会调用你

最后谈一下和策略模式的区别,最主要的区别是一个是使用继承而策略模式是使用组合方式。

你可能感兴趣的:(设计模式之template method模式)