模板方法模式
Define the skeleton of an algorithm in an operation,deferring some steps to subclasses.
Template method lets subclass redefine certain steps of an algorithm without changing
the algorithm structure.
在操作中定义算法的骨架,将一些步骤推迟到子类实现。
模板方法允许子类在不改变算法结构的情况下重新定义算法的某些步骤。
@Slf4j
public class Template {
/**
* 模板方法模式:
* Define the skeleton of an algorithm in an operation,deferring some steps to subclasses.
* Template method lets subclass redefine certain steps of an algorithm without changing
* the algorithm structure.
* 在操作中定义算法的骨架,将一些步骤推迟到子类实现。
* 模板方法允许子类在不改变算法结构的情况下重新定义算法的某些步骤。
*/
@Test
public void all() {
final Message message = Message.builder().title("template pattern").content("hello world").copyRight("版权所有 ZXD 15505883728").needTitle(true).build();
final TextBuilder textBuilder = TextBuilder.builder().message(message).build();
String msg = textBuilder.build();
log.info(msg);
message.setNeedTitle(false);
final HtmlBuilder htmlBuilder = HtmlBuilder.builder().message(message).build();
msg = htmlBuilder.build();
log.info(msg);
}
}
/**
* 1)抽象模板类,定义算法的基本步骤和算法的骨架
*/
abstract class ABuilder {
/**
* 以下方法为算法的基本步骤
*/
abstract String title();
abstract String content();
abstract String copyRight();
// 基于 title 的钩子函数,允许修改算法的逻辑
abstract boolean needTitle();
/**
* 算法骨架需要定义为 final 类型,不允许子类修改。
*/
public final String build() {
final StringJoiner joiner = new StringJoiner("\r\n");
if (needTitle()) {
joiner.add(title());
}
return joiner.add(content()).add(copyRight()).toString();
}
}
@Data
@Builder
class Message {
private String title;
private String content;
private String copyRight;
private boolean needTitle;
}
/**
* 2)实现算法的基本步骤以构建特定的实例。
*/
@Builder
class TextBuilder extends ABuilder {
private final Message message;
@Override
String title() {
return message.getTitle();
}
@Override
String content() {
return message.getContent();
}
@Override
String copyRight() {
return message.getCopyRight();
}
@Override
boolean needTitle() {
return message.isNeedTitle();
}
}
/**
* 3)实现算法的基本步骤以构建特定的实例。
*/
@Builder
class HtmlBuilder extends ABuilder {
private final Message message;
@Override
String title() {
return new StringJoiner("").add("<html><head><title>Empty</title><body><h3>").add(message.getTitle())
.add("</h3>").toString();
}
@Override
String content() {
return new StringJoiner("").add("<h5>").add(message.getContent()).add("</h5>").toString();
}
@Override
String copyRight() {
return new StringJoiner("").add("<h6>").add(message.getCopyRight()).add("</h6>").toString();
}
@Override
boolean needTitle() {
return message.isNeedTitle();
}
}