java 设计模式之模板方法模式(十二)

奋斗不一定全是为了钱,还有骨子里那份自信、淡定、从容!买得起自己喜欢的东西,去的了自己想去的地方,能承担起该承担的责任,花自己的钱,过有质量的生活!做一个无可替代的自己!

定义

模板方法模式定义了一个算法的步骤,并允许子类别为一个或多个步骤提供其实践方式。让子类别在不改变算法架构的情况下,重新定义算法中的某些步骤。在软件工程中,它是一种软件设计模式,和C++模板没有关连。

设计模式学习,近期我会把23种设计模式都写成博客,敬请期待~
—2021/1/15

百度百科

使用场景

我现在要制作豆浆,首先我需要:

  • 准备黄豆子
  • 准备红豆,黄豆,黑豆
  • 加冰糖
  • 打磨成豆浆

大致分为这几步.

按照总体来说,豆浆制作过程基本相同,只是放的配料不一样,我要喝红豆豆浆,就放红豆,我要喝黄豆豆酱就放黄豆,最后也可以选择加不加冰糖,这里就用到了模板方法模式.

思路分析

模板方法模式就是通过定义一个模板,来规范代码的流程

UML类图(1.1):
在这里插入图片描述
通过定义ATemplate抽象方法,来规范豆浆制作过程,其子类BlackSoybeanMilkImpl实现了放什么豆子,这里放入黑豆,就打出的是黑豆浆.

角色分析

  • ATemplate(抽象类):类中实现了模板,定义了整体代码思路骨架,具体代码子类实现,
  • BlackSoybeanMilkImpl(实现类):实现了具体代码
  • 客户端:客户端直接调用实现类,然后使用多态的机制,调用父类的模板方法

代码实现

ATemplate抽象类,定义代码规范:

public abstract class ATemplate {
    
    

    //用来规范豆浆流程
    void aemplate() {
    
    
        soybean();//准备黄豆
        addBean();//添加豆子
        sugar();  //准备冰糖
        polish(); //打豆浆
    }
    //准备黄豆
   private void soybean() {
    
    
        Log.i("模板方法模式 ","准备黄豆");
    }

    //添加豆子
    public abstract void addBean();

    //准备冰糖
    private void sugar() {
    
    
        Log.i("模板方法模式 ","放入冰糖");
    }

    //打豆浆
    private void polish() {
    
    
        Log.i("模板方法模式 ","开始打磨豆浆 预计10分钟完毕");
    }
}

BlackSoybeanMilkImpl黑豆实现:

public class BlackSoybeanMilkImpl extends ATemplate{
    
    

    @Override
    public void addBean() {
    
    
        Log.i("模板方法模式 ","放入 黑豆浆");
    }
}

RedSoybeanMilkImpl黄豆实现:

public class RedSoybeanMilkImpl extends ATemplate{
    
    
    @Override
    public void addBean() {
    
    
        Log.i("模板方法模式 ","放入 红豆浆");
    }
}

客户端(测试代码):

//制作黑豆浆
ATemplate blackSoybeanMilk = new BlackSoybeanMilkImpl();
blackSoybeanMilk.aemplate();

Log.i("模板方法模式 "," ===========================");

//制作红豆浆
RedSoybeanMilkImpl redSoybeanMilk = new RedSoybeanMilkImpl();
redSoybeanMilk.aemplate();

Log图(2.1):
在这里插入图片描述

钩子方法理解

还是上边的例子,如果我现在想喝纯豆浆,不加糖,这里就用到了钩子"

钩子方法作用: 标识是否执行某一段代码;

钩子代码实现

ATemplate添加钩子方法isSugar():

public abstract class ATemplate {
    
    
    //用来规范豆浆流程
    void aemplate() {
    
    
        soybean();//准备黄豆
        addBean();//添加豆子
        if (isSugar()) {
    
    
            sugar();  //准备冰糖
        }
        polish(); //打豆浆
    }
    //准备黄豆
    private void soybean() {
    
    
        Log.i("模板方法模式 ", "准备黄豆");
    }

    //添加豆子
    public abstract void addBean();

    //准备冰糖
    private void sugar() {
    
    
        Log.i("模板方法模式 ", "放入冰糖");
    }

    //打豆浆
    private void polish() {
    
    
        Log.i("模板方法模式 ", "开始打磨豆浆 预计10分钟完毕");
    }

    //默认加糖 钩子方法
    public boolean isSugar() {
    
    
        return true;
    }
}

PureSoybeanMilkImpl纯豆浆制作:

重写钩子方法(),修改为不加糖:

public class PureSoybeanMilkImpl extends ATemplate{
    
    
    @Override
    public void addBean() {
    
    
        Log.i("模板方法模式 ","我这里什么都不加,我要喝纯豆浆");
    }
    //不加糖
    @Override
    public boolean isSugar() {
    
    
        return false;
    }
}

客户端(测试代码):

//制作黑豆浆
ATemplate blackSoybeanMilk = new BlackSoybeanMilkImpl();
blackSoybeanMilk.aemplate();

Log.i("模板方法模式 "," ===========================");

//制作红豆浆
RedSoybeanMilkImpl redSoybeanMilk = new RedSoybeanMilkImpl();
redSoybeanMilk.aemplate();


Log.i("模板方法模式 "," ===========================");

//制作纯豆浆  使用钩子 不加糖
PureSoybeanMilkImpl pureSoybeanMilk = new PureSoybeanMilkImpl();
pureSoybeanMilk.aemplate();

Log图(2.2):
在这里插入图片描述

总结:

  • 模板方法模式还是比较简单的,就是通过一个抽象类规范了代码的流程,具体需要改变的地方,写成抽象方法,让其子类去实现,

  • 钩子就是模板方法抽象类中的一个’方法变量’,标识是否执行某一段代码;

完整代码

去设计模式/设计原则主页

原创不易,您的点赞就是对我最大的支持~

猜你喜欢

转载自blog.csdn.net/weixin_44819566/article/details/112651624