定义一个操作中的算法的骨架,而将一些步骤延迟到子类中实现。TemplateMethod使得子类可以不改变一个算法的结构即可重定义该算法的某些特定步骤。
Template Method
英文简要描述
Intent
Define the skeleton of an algorithm in an operation, deferring some steps to subclasses.
Template Method lets subclasses redefine certain steps of an algorithm without changing the algorithm's structure.
How to
AbstractClass
defines abstract primitive operations that concrete subclasses define to implement steps of an algorithm.
implements a template method defining the skeleton of an algorithm. The template method calls primitive operations as well as operations defined in AbstractClass or those of other objects.
ConcreteClass
implements the primitive operations to carry out subclass-specific steps of the algorithm.
Known cases
A lot
UML
模板方法通常和工厂方法一起使用,以下是样例:
public abstract class Application {
private List docs = new ArrayList();
public Document openDocument(String path) {
Document doc = null;
if (isDocumentExist(path)) {
doc = newDocument();
} else {
doc = readDocument(path);
}
appendDocument(doc);
check(doc);
return doc;
}
private boolean isDocumentExist(String path) {
// check if the document exists
// ...
return true;
}
private void appendDocument(Document doc) {
docs.add(doc);
}
protected abstract Document newDocument(); // factory method
protected abstract Document readDocument(String path); //primitive method
protected void check(Document doc) { // hook method
// do thing
}
}
public class ExcelApplication extends Application {
protected Document newDocument() {
return new ExcelDocument();
}
protected Document readDocument(String path) {
System.out.println("Read Excel Document");
return null;
}
protected void check(Document doc) {
System.out.println("Check Excel Document");
}
}
public class WordApplication extends Application {
protected Document newDocument() {
return new WordDocument();
}
protected Document readDocument(String path) {
System.out.println("Read Word Document");
return null;
}
}
public interface Document {
public void show();
}
public class ExcelDocument implements Document {
public void show() {
System.out.println("Show Excel Document");
}
}
public class WordDocument implements Document {
public void show() {
System.out.println("Show Word Document");
}
}
public class TestTemplateMethod {
public static void main(String[] args) {
Application app = null;
if (args[0].equals("Word")) {
app = new WordApplication();
} else if (args[0].equals("Excel")) {
app = new ExcelApplication();
} else {
throw new RuntimeException("Unsupport type");
}
Document doc = app.openDocument("Path");
doc.show();
}
}
primitive operation
抽象方法,子类必须实现
hook operation
钩子方法,有默认实现,子类可以重写其行为
板方法模式可以解决某些场合的代码冗余问题,但是也可能引入子类泛滥的问题。虽然引入了回调方法,但是如果回调实现的接口过多,代码较为复杂,这些代码拥挤在一起回引起阅读困难的问题。