浅谈设计模式--模板方法模式

    最近刚刚学习了设计模式之模板方法模式,趁着热乎劲,一点小心得分享给大家,抛砖引玉,欢迎评论区讨论!    所谓模板方法,就是利用java的继承机制,在父类中定义一套算法框架,封装到一个模板方法当中,以达到父类控制算法流程的目的。一般为了防止该模板方法被覆盖,通常被声明为final。    例如,完成一套咖啡因饮料的冲泡步骤如下:        1.把水煮沸        2.冲泡咖啡/浸泡茶叶        3.倒进杯子        4.加糖和牛奶/加柠檬     假如饮料店老板希望加盟店严格按照这套步骤来完成饮料的制作,这时候就可以定义一个模板方法,所有的子类必须继承这个方法,以达到控制工序的目的。    大家可能注意到,不论是冲泡茶还是煮咖啡,第一步和第三步都是一样的,这时候就可以将这两个方法在父类中给出定义;而对于有变化的步骤,可以定义为抽象,供子类实现。此时的抽象父类如下:public abstract class CoffeeBeverage {

   final void prepareRecipe() {
       boilWater();
       brew();
       pourInCup();
       addCondiments();
   }

   abstract void brew();

   abstract void addCondiments();

   void boilWater() {
       System.out.println("Boiling water...");
   }

   void pourInCup() {
       System.out.println("Pouring in the cup...");
   }
}        继承咖啡因饮料的子类只需覆写抽象的brew()和addCondiments()方法即可调用prepareRecipe()方法制作一杯美味的饮料!        下面我们就来制作一杯香浓的咖啡吧:public class Coffee extends CoffeeBeverage {
   @Override
   void brew() {
       System.out.println("Dripping coffee through the filter...");
   }

   @Override
   void addCondiments() {
       System.out.println("Adding sugar and milk...");
   }
}public class Runner {
   public static void main(String[] args) {
       System.out.println("I will prepare a cup of coffee for you!");
       Coffee coffee = new Coffee();
       coffee.prepareRecipe();
}         我们惊喜的发现:模板方法使得子类在不改变算法结构的情况下,重新定义了算法的某些步骤!         但是模板方法的作用仅限于此吗?并不是的,其实,我们还可以在模板方法中定义什么默认都不做的方法。我们把这种方法称之为“hook”(钩子)。当然,什么都不做不代表没有用,子类可以视情况决定要不要覆盖它们。        顾名思义,hook方法存在的意义在于使子类有能力对对算法的不同点进行挂钩,达到控制是否执行某部分算法的目的。         下面的代码,你可以来泡一杯茶,而是否加柠檬(addCandidents()),决定权在你的手里了,想想是不是还有点小激动呢!        public abstract class CoffeeBeverage {

   final void prepareRecipe() {
       boilWater();
       brew();
       hook();
       pourInCup();
       concreteOperation();
   }

   abstract void brew();

   abstract void addCondiments();

   void boilWater() {
       System.out.println("Boiling water...");
   }

   void pourInCup() {
       System.out.println("Pouring in the cup...");
   }

   final void concreteOperation() {

   }

   //钩子方法能够决定程序内部算法
   void hook() {
       if (customerWantsCondiment()) {
           addCondiments();
       }
   }
   protected abstract boolean customerWantsCondiment();public class Tea extends CoffeeBeverage {
   @Override
   void brew() {
       System.out.println("Steeping the tea...");
   }

   @Override
   void addCondiments() {
       System.out.println("Adding lemon...");
   }

   @Override
   protected boolean customerWantsCondiment() {
       try {
           System.out.println
                   ("Would you like to add some condiments?");
           BufferedReader bufferedReader =
                   new BufferedReader(new InputStreamReader
                           (System.in));
           String s = bufferedReader.readLine();
           if (s.toLowerCase().startsWith("y")) {
               return true;
           } else {
               return false;
           }
       } catch (Exception e) {
           e.printStackTrace();
           return false;
       }
   }
}public class Runner {
   public static void main(String[] args) {
       Tea tea = new Tea();
       tea.prepareRecipe();
   }
}        程序运行,一杯浓香的茶又来到了你的手中。         总结:通过以上的例子可以看到,模板方法这个设计模式简直棒极了!它由框架来控制如何做事情,而允许你来指定框架算法中的每个步骤的细节。  

相关内容推荐