编程设计模式之模板方法模式
为什么有模板方法模式?
在软件开发中,有时候我们会遇到一些算法框架,其中一些步骤是固定的,而另一些步骤则可能因应用场景不同而变化。如果每次都直接在代码中硬编码这些固定的步骤,会导致代码的重复和扩展困难。模板方法模式就是为了解决这一问题而诞生的。
模板方法模式的设计思路
模板方法模式定义了一个算法的骨架,将具体步骤的实现延迟到子类中。它包含两种类型的方法:
- 模板方法(Template Method):定义了算法的骨架,其中包含了算法的主要逻辑,调用了一系列的抽象方法,这些抽象方法需要在具体子类中实现。
- 钩子方法(Hook Method):在模板方法中被声明并提供默认实现,子类可以选择性地覆盖它们来扩展或修改算法的行为。
模板方法模式包含三个主要角色:
- AbstractClass(抽象类):定义了一个模板方法,其中包含算法的骨架和一些抽象方法,这些抽象方法由具体子类来实现。
- ConcreteClass(具体子类):实现了抽象类中的抽象方法,完成算法的具体步骤。
- Hook Method(钩子方法):在抽象类中提供了默认的实现,子类可以选择性地覆盖它们。
Java示例代码
下面是一个简单的Java示例代码,演示了模板方法模式的应用:
java
// 抽象类
abstract class AbstractClass {
// 模板方法
public final void templateMethod() {
primitiveOperation1();
primitiveOperation2();
hookMethod();
}
// 基本方法1(抽象方法)
abstract void primitiveOperation1();
// 基本方法2(抽象方法)
abstract void primitiveOperation2();
// 钩子方法(默认实现)
void hookMethod() {
System.out.println("钩子方法默认实现");
}
}
// 具体子类A
class ConcreteClassA extends AbstractClass {
@Override
void primitiveOperation1() {
System.out.println("具体子类A中的基本方法1的实现");
}
@Override
void primitiveOperation2() {
System.out.println("具体子类A中的基本方法2的实现");
}
@Override
void hookMethod() {
System.out.println("具体子类A中的钩子方法的实现");
}
}
// 具体子类B
class ConcreteClassB extends AbstractClass {
@Override
void primitiveOperation1() {
System.out.println("具体子类B中的基本方法1的实现");
}
@Override
void primitiveOperation2() {
System.out.println("具体子类B中的基本方法2的实现");
}
}
// 客户端代码
public class Main {
public static void main(String[] args) {
AbstractClass concreteClassA = new ConcreteClassA();
concreteClassA.templateMethod();
AbstractClass concreteClassB = new ConcreteClassB();
concreteClassB.templateMethod();
}
}
SpringBoot工程中如何应用模板方法模式
在SpringBoot工程中,模板方法模式常被用于定义一些基础的流程或骨架,并在具体子类中实现特定的业务逻辑。例如,Spring框架中的JdbcTemplate就是一个典型的模板方法模式的应用。
下面是一个简单的示例,演示了如何在SpringBoot工程中应用模板方法模式:
java
import org.springframework.jdbc.core.JdbcTemplate;
// 抽象模板类
abstract class JdbcOperationTemplate {
protected final JdbcTemplate jdbcTemplate;
public JdbcOperationTemplate(JdbcTemplate jdbcTemplate) {
this.jdbcTemplate = jdbcTemplate;
}
// 模板方法
public final void execute() {
openConnection();
doOperation();
closeConnection();
}
// 抽象方法:打开连接
protected abstract void openConnection();
// 抽象方法:执行操作
protected abstract void doOperation();
// 抽象方法:关闭连接
protected abstract void closeConnection();
}
// 具体子类:查询操作
class QueryOperation extends JdbcOperationTemplate {
public QueryOperation(JdbcTemplate jdbcTemplate) {
super(jdbcTemplate);
}
@Override
protected void openConnection() {
System.out.println("打开数据库连接");
}
@Override
protected void doOperation() {
jdbcTemplate.query("SELECT * FROM table", (rs, rowNum) -> {
// 处理结果集
return null;
});
}
@Override
protected void closeConnection() {
System.out.println("关闭数据库连接");
}
}
// 客户端代码
public class Main {
public static void main(String[] args) {
JdbcTemplate jdbcTemplate = new JdbcTemplate(); // 实际项目中应该从Spring容器中注入
JdbcOperationTemplate operation = new QueryOperation(jdbcTemplate);
operation.execute();
}
}
通过这种方式,在SpringBoot工程中,我们可以定义一些通用的数据库操作流程,并通过具体的子类来实现特定的业务逻辑,实现代码的复用和灵活性。