
一、介绍
官方解释:定义一个操作中算法的框架,而将一些步骤延迟到子类中。模板方法模式使得子类可以不改变一个算法的结构即可重定义该算法的某些特定步骤。
设计模式大咖闫宏解释:模板方法模式是类的行为型模式。准备一个抽象类,将部分逻辑以具体方法以及具体构造函数的形式实现,然后声明一些抽象方法来迫使子类实现剩余的逻辑。不同的子类可以以不同的方式实现这些抽象方法,从而对剩余的逻辑有不同的实现。这就是模板方法模式的用意。
个人理解:模板方法模式是基于继承结构的一种行为型模式,模板就是这个模式中的抽象父类,父类的方法中,有一个定义了算法框架(方法执行顺序)的模板方法,这些框架之下的方法由子类去进行实现、重写或直接运用,从而使得相同的算法框架可以有不同的执行结果,也是一种多态思想的体现
二、角色
-
抽象类(AbstractClass):抽象类实现了模板方法,定义了算法的框架,其中的方法可以是具体方法也可以是抽象方法(其中抽象方法称为基本操作,算法的框架称为模板方法)
-
具体子类(ConcreteClass):继承抽象类,实现了抽象类中的抽象方法从而完成子类特定的算法,也可以选择是否重写父类中的具体方法
三、模板抽象类的实现方法
-
**抽象方法:**由抽象类声明,由具体子类实现。
-
**具体方法:**具体方法由抽象类声明并实现,而子类并不实现或置换。
-
**钩子方法:**钩子方法是由抽象类声明并实现,子类会选择是否应用或是否加以扩展。钩子方法一般有两种实现方式
第一种方式是由抽象类给出空实现
javapublic void printQianYan(){}第二种方式可以这样使用挂钩,让子类决定里面的代码是否执行
抽象类中默认给出false ,如果子类需要使用可以重写hook方法 改为 返回ture
javaif(hook()){ //打印前言 printQianYan(); } public boolean hook() { return false; }
钩子方法典型代码
java
//模板方法
public void TemplateMethod()
{
Open();
Display();
//通过钩子方法来确定某步骤是否执行
if (IsPrint())
{
Print();
}
}
//钩子方法
public bool IsPrint()
{
return true;
}
}
四、案例
定义接口 这一步不是必须的
java
public interface Bank {
void handleBusiness();
}
抽象类(AbstractClass)
java
public abstract class AbstractBank implements Bank{
// 定义算法
@Override
public final void handleBusiness() {
drawNumber();
callNum();
doBusiness();
if (isFeedback()) {
feedBack();
}
}
private void drawNumber () {
System.out.println("用身份证抽取号码");
}
protected abstract void doBusiness(); // 交给子类实现
private void callNum () {
System.out.println("叫号到柜台办理业务");
}
private void feedBack () {
System.out.println("反馈");
}
// 钩子方法
public boolean isFeedback() {
return false;
}
}
具体子类(ConcreteClass)
java
public class SaveMoney extends AbstractBank{
@Override
protected void doBusiness() {
System.out.println("存钱成功");
}
@Override
public boolean isFeedback() {
return true;
}
}
java
public class TakeMoney extends AbstractBank{
@Override
protected void doBusiness() {
System.out.println("取钱走人");
}
}
测试 一般取钱走人 不执行反馈

可以看出,不同的子类实现了自己的特定算法,我们知道了,模板模式的关键就是:子类置换了父类的可变部分(即抽象方法),但是仍然依据在父类的框架之下
五、优缺点
优点
-
模板方法模式将不变的行为抽提到了父类中,去除了子类中的重复代码。
-
子类可以自由实现抽象算法中的具体细节,有助于算法的扩展。
-
模板方法模式运用了多态,又称向上转型,这种结构也被称为"好莱坞法则" ,即"别找我们,,用你的时候我们找你",通过一个父类调用其子类的操作(而不是相反的子类调用父类),通过对子类的扩展增加新的行为,符合"开闭原则"。
** 缺点**
- 每个不同的实现都需要定义一个子类,这会导致类的个数的增加,系统不容易管理
六、解决的问题类型
模板方法模式主要用于解决以下问题:
-
多个类实现同一个算法,但部分步骤不同:为了避免代码重复,提取公共流程。
-
希望统一算法结构,控制子类的行为边界:防止子类修改关键流程。
-
需要封装不变部分,扩展可变部分:提高代码复用性和可维护性
七、与策略模式对比
| 对比点 | 模板方法模式 | 策略模式 |
|---|---|---|
| 实现方式 | 继承(父类定义流程) | 组合(对象持有策略) |
| 扩展性 | 通过继承扩展 | 通过接口实现替换 |
| 运行时切换 | 不易动态切换流程 | 可在运行时更换策略 |
| 耦合度 | 父子类紧耦合 | 客户端与策略松耦合 |
总结
模板方法模式是由抽象父类定义执行框架,然后由子类去实现方法的具体细节。当某些类的算法中用了相同的算法,造成代码的重复的时候,就可以考虑应用模板方法模式了。也特别适用于那些流程固定但细节可变的业务场景。它通过"封装不变,扩展可变"的思想,帮助开发者构建结构清晰、易于维护的系统
