战争打到现在已经基本清理完 【创建型】 和【结构型】军团,结构型还差一个 Composite组合模式身居敌方阵营中心。无伤大雅,等我们登上光明顶,搞死他。现在敌军已经孤立无援,只剩下【行为型】军团。看我们一枪一个小朋友。赢得最终胜利~ 已瞄准:模板方法模式 看门狗,请指示~ 开炮!!!!!
十二、设计模式之模板方法模式
所属类型 | 定义 |
---|---|
行为型 | 模板方法模式定义了一个算法的步骤,并允许子类别为一个或多个步骤提供其实践方式。让子类别在不改变算法架构的情况下,重新定义算法中的某些步骤 |
能帮我们干什么?
主要解决什么问题?
主要解决的是 一些方法通用,却在每一个子类都重新写了这一方法。
**何时使用:**有一些通用的方法。
**如何解决:**将这些通用算法抽象出来。
优缺点
优点
1、封装不变部分,扩展可变部分。
2、提取公共代码,便于维护。
3、行为由父类控制,子类实现。
缺点:
每一个不同的实现都需要一个子类来实现,导致类的个数增加,使得系统更加庞大。
使用的场景
- 有多个子类共有的方法,且逻辑相同。
- 重要的、复杂的方法,可以考虑作为模板方法。
实现
模板方法模式
难度: ⭐️
样例代码
描述:
学生都有吃和睡都是一样的。
但是好学生的学习和坏学生的学习方法就不一样了。
我们就可以引入模板方法模式,把学生 吃和睡的能力抽象出来。而学习的方法延迟给具体的学生子类自己实现。
模板方法类:学生
public abstract class Student {
protected String name;
public Student(String name) {
this.name = name;
}
/**
* 通用方法吃 final 控制稳定性
*
* @param food
*/
public final void eat(String food) {
System.out.println(name + " 吃 饭:" + food);
}
/**
* 通用方法睡觉
* final 控制稳定性
*
* @param sleepTime
*/
public final void sleep(int sleepTime) {
System.out.println(name + "睡觉:" + sleepTime + "小时");
}
/**
* 学习方法由不同学生不同实现
* 延迟到子类实现
*/
public abstract void study();
}
实现类: 好学生
/**
* 三好学生(学霸)
* 有自己的学习方法*/
public class SanHaoStudent extends Student {
public SanHaoStudent(String name) {
super(name);
}
@Override
public void study() {
System.out.println( super.name +"说: 太简单了,微积分轻轻松松满分! 10分钟就学会了。真简单!打游戏上王者");
}
}
实现类:坏学生
/**
* 学渣的学习方法
*/
public class BadStudent extends Student {
public BadStudent(String name) {
super(name);
}
@Override
public void study() {
System.out.println(name + ": 微积分TMD真难呀。学了23个小时了。一道题都没做出了。算了,打游戏吧,三好学生上线,带带我");
}
}
使用客户端
public static void main(String[] args) {
Student zhangsan = new SanHaoStudent("zhangsan");
Student lisi = new BadStudent("lisi");
// 吃早餐
zhangsan.eat("早餐:牛奶");
lisi.eat("早餐:牛奶 + 可乐 + 牛腿");
// 学习
zhangsan.study();
lisi.study();
// 睡觉
zhangsan.sleep(10);
lisi.sleep(1);
}
总结
模板方法模式可以帮我们抽象出流程的行为规范。并指定某些行为必须由子类完成。达到整个流程的完整性和过程中的可变性。
**注意事项:**为防止恶意操作,一般模板方法都加上 final 关键词