美文网首页
模板方法模式(Template Method)

模板方法模式(Template Method)

作者: Febare | 来源:发表于2021-08-09 11:05 被阅读0次

    定义

    模板方法模式 在一个方法中定义一个算法的骨架,而将一些步骤延迟到子类中。模板方法使得子类可以在不改变算法结构的情况下,重新定义算法中的某些步骤。它是一种类行为型模式。

    这个模式是用来创建一个算法的模板。什么是模板? 模板就是一个方法。更具体地说,这个方法将算法定义成一组步骤,其中的任何步骤都可以是抽象的,由子类负责实现。这可以确保算法的结构保持不变,同时由子类提供部分实现。

    特点

    • 封装不变的部分,扩展可变的部分。不变部分的算法封装到父类中实现,而把可变部分算法由子类继承实现,便于子类继续扩展。
    • 父类提取公共部分的代码,避免子类出现重复代码。
    • 父类的抽象方法由子类实现,子类执行的结果会影响父类的结果。
    • 由于继承关系自身的缺点,当父类添加新抽象方法时,所有子类都必须实现新增的抽象方法。

    UML结构

    f1x939.png

    Code结构

    // 抽象类
    abstract class AbstractClass {
        // 模板方法,定义了一个算法的步骤,避免子类干扰步骤,使用final进行方法修饰
        public final void templateMethod() {
            primitiveOperation1();
            primitiveOperation2();
            concreteOperation();
            hook();
        }
        
        // 抽象类方法,必须由子类进行具体实现
        abstract void primitiveOperation1();
        
        // 抽象类方法,必须由子类进行具体实现
        abstract void primitiveOperation2();
        
        // 具有共性的由父类直接实现,同时使用final修饰避免子类覆盖它
        public final void concreteOperation() {
            // 这里是实现
        }
        
        // 当子类必须提供算法中某个方法或步骤的实现,并且这个实现为可选调用时就可以使用钩子方法 
        void hook() {}
    }
    
    // 具体子类
    class ConcreteClass extends AbstractClass {
        public void primitiveOperation1() {
            System.out.println("抽象方法1的实现被调用...");
        }
        public void primitiveOperation2() {
            System.out.println("抽象方法2的实现被调用...");
        }
    }
    
    public static void main(String[] args) {
        AbstractClass tm = new ConcreteClass();
        tm.templateMethod();
    }
    

    场景示例

    /**
     * 咖啡因饮料模板类
     */
    public abstract class CaffeineBeverages {
        /*
         * 模板方法
         * 封装了制作咖啡因饮料过程的算法框架
         */
        public final void driveTemplate(){
            // 1.将水煮沸
            boilWater();
            // 2. 炮制饮料
            blew();
            // 3. 倒入杯中
            pourInCup();
            // 钩子函数 判定(例如茶不想加入调味料)
            if(isRight()){
                // 4. 进入调味料
                addCondiments();
            }
        }
    
        /*
         * 基本方法,将水煮沸
         */
        private void boilWater() {
            System.out.println("将水煮沸");
        }
    
        /*
         * 基本方法,倒入杯中
         */
        private void pourInCup() {
            System.out.println("倒入杯中");
        }
    
        /*
         * 抽象方法 加入调味料(可选)
         * 需由子类实现
         */
        public abstract void addCondiments();
    
        /*
         * 抽象方法 炮制饮料(可选)
         * 需由子类实现
         */
        public abstract void blew();
    
        // 钩子函数 判断用户是否要执行某些 “可选” 功能  
        public boolean isRight(){
            return true;
        }
    }
    
    /**
     * 制备茶的具体实现类
     */
    public class Tea extends CaffeineBeverages {
        // 添加调料
        @Override
        public void addCondiments() {
            System.out.println("加入柠檬");
        }
        // 冲泡茶
        @Override
        public void blew() {
            System.out.println("用80度的热水浸泡茶叶5分钟");
        }
        // 重写钩子函数 改变其值
        @Override
        public boolean isRight(){
            return false;
        }
    }
    

    相关文章

      网友评论

          本文标题:模板方法模式(Template Method)

          本文链接:https://www.haomeiwen.com/subject/bxhzvltx.html