模板,顾名思义,就是定义了做一件事的步骤,比如做一道菜,规定为,先洗菜,再切菜,再烹饪调味,再装盘。
模板就事把上面的做一道菜的步骤定死了,但是具体洗菜怎么洗,切菜怎么切,推迟到子类实现。
为了让说明更清晰我们就以做菜来作为示例,实现模板方法模式。
上代码:
首先要定义一个模板,最好定义模板的就是抽象类了
public abstract class AbstractCooking {
/**
* 洗菜
*/
public abstract void wash();
/**
* 切菜
*/
public abstract void cut();
/**
* 烹饪
*/
public abstract void cook();
/**
* 装盘
*/
public abstract void onPalte();
/**
* 这里定死做一道菜的步骤
* 也就是定义算法框架,算法框架一般是定死的,不能被重写的,所以用final修饰
* 这个方法也被称为模板方法,模式的名称就是因此得名
*/
public final void makeFood(){
this.wash();
this.cut();
this.cook();
this.onPalte();
}
}
注意上面代码的模板算法,步骤定死,然后不能被重写。
接下来是具体的模板实现类:
public class MeatCooking extends AbstractCooking {
@Override
public void wash() {
System.out.println("洗肉");
}
@Override
public void cut() {
System.out.println("切肉");
}
@Override
public void cook() {
System.out.println("炒肉");
}
@Override
public void onPalte() {
System.out.println("肉装盘");
}
}
public class TomatoCooking extends AbstractCooking {
@Override
public void wash() {
System.out.println("洗番茄");
}
@Override
public void cut() {
System.out.println("切番茄");
}
@Override
public void cook() {
System.out.println("煮番茄");
}
@Override
public void onPalte() {
System.out.println("番茄装盘");
}
}
客户端测试代码:
public class TemplateTest {
public static void main(String[] args) {
AbstractCooking meatCooking = new MeatCooking();
meatCooking.makeFood();
System.out.println();
AbstractCooking tomatoCooking = new TomatoCooking();
tomatoCooking.makeFood();
}
}
然后是测试结果:
洗肉
切肉
炒肉
肉装盘
洗番茄
切番茄
煮番茄
番茄装盘
看了代码之后,肯定会发现,模板模板,就是给你模板自己去完善。
所以模板有以下优点:
1、封装不变部分(模板方法是不变的,不可重写),扩展可变部分(算法细节可以扩展)。
2、提取公共代码(模板方法),便于维护。
3、行为由父类控制,子类实现。
当然又优点就有缺点
缺点: 每一个不同的实现都需要一个子类来实现,导致类的个数增加,使得系统更加庞大。
模板方法的使用场景:
1、有多个子类共有的方法,且逻辑相同。 2、重要的、复杂的方法,可以考虑作为模板方法。
需要特别注意事项: 为防止恶意操作,一般模板方法都加上 final 关键词。