《Head First设计模式》 读书笔记09 模板方法模式 The Template Method Pattern

 

《Head First设计模式》 读书笔记09 模板方法模式

The Template Method Pattern

 

问题引入

  咖啡和茶的冲泡步骤都差不多,可以理解为两份冲泡法都采用了基本相同的算法:

    1.煮沸水。

    2.用热水泡茶或咖啡。

    3.把饮料倒进杯子。

    4.加入适当调料(奶、糖或者柠檬片)。

  如果实现不好,就会有重复的代码,算法的知识和实现会分散在许多类中,算法修改不容易,并且加入新种类的饮料也需要做很多工作。

 

  那该怎么设计呢?

  采用一个新的基类(咖啡因饮料类),其中有一个声明为final的方法(不希望被子类覆盖),为冲泡饮料的动作。

  该方法(也就是模板方法)中包含了若干个小方法调用,这些小方法就是一个个基本的步骤。

  对于这些步骤的处理:对各个类相同的子步骤在基类定义;而咖啡和茶有区别的步骤,声明为虚函数,依赖子类(咖啡类和茶类)自己去完成。

 

 

  上面的图中,prepareRecipe()就是我们的模板方法

  它用作一个算法的模板,在这个模板中,算法内的每一个步骤都被一个方法代表了。

  某些方法是由超类处理的,某些方法留给子类处理,这些需要由子类提供的方法,必须在超类中声明为抽象。

 

  模板方法定义了一个算法的步骤,并允许子类为一个或多个步骤提供实现。

 

模板方法模式定义

  模板方法模式在一个方法中定义一个算法的骨架,而将一些步骤延迟到子类中。

  模板方法使得子类可以在不改变算法结构的情况下,重新定义算法中的某些步骤。

  模板方法非常常见,对创建框架来说,由框架控制如何做事情,而由你(使用这个框架的人)指定框架算法中每个步骤的细节。(可以想想单元测试的框架JUnit的实现。)

 

对模板方法进行挂钩

  钩子(hook)是一种被声明在抽象类中的方法,但只有空的或者默认的实现

  钩子的存在,可以让子类有能力对算法的不同点进行挂钩。要不要挂钩,由子类自行决定。

  某些步骤是可选的,所以可以将这些步骤实现成钩子,而不是实现成抽象方法,这样就可以让抽象类的子类的负荷减轻。

  比如,也可以利用钩子做条件控制,影响抽象类中的算法流程:钩子方法在抽象类中有默认实现返回true,放在抽象类的if条件语句中,子类可以覆盖也可以不覆盖这个钩子方法。

 

好莱坞原则

  好莱坞原则:别调用(打电话给)我们,我们会调用(打电话给)你。

  好莱坞原则可以给我们一种防止“依赖腐败”的方法。

  当组件之间太多依赖的时候,设计就变得难懂了。

 

  在好莱坞原则之下,我们允许低层组件将自己挂钩到系统上,但是高层组件会决定什么时候和怎样使用这些低层组件。

  换句话说,高层组件对待低层组件的方式是“别调用我们,我们会调用你”

 

好莱坞原则和依赖倒置原则

  依赖倒置原则教我们尽量避免使用具体类,而多使用抽象。

  而好莱坞原则是用在创建框架或组件上的一种技巧,好让低层组件能够被挂钩进计算中,而且又不会让高层组件依赖底层组件。

  两者的目标都是在于解耦

 

模板方法模式和其他模式

  策略模式和模板方法模式都封装算法,一个用组合,一个用继承。

  工厂方法是模板方法的一种特殊版本。

posted @ 2013-05-04 17:22  圣骑士wind  阅读(480)  评论(0编辑  收藏  举报