一、模式定義
模板模式(Template Pattern)是一種行爲設計模式,它在超類中定義了一個算法的框架,允許子類在不修改結構的情況下重寫算法的特定步驟。
二、模式動機
許多業務有着相同的算法/步驟骨架,這些算法/步驟中有許多是相同的實現要求,部分步驟是要求不同的實現。
此時就可以在超類/抽象類中定義算法和步驟,提供程序的方法主入口。由超類/抽象類來實現通用的步驟方法,超類/抽象類無法實現的具體步驟交給子類來實現。
三、模式結構
模板模式的角色:
- 抽象模板角色:抽象模板類,定義了一個具體的算法流程和一些留給子類必須實現的抽象方法。
- 具體子類角色:實現抽象模板類中的抽象方法,子類可以有自己獨特的實現形式,但是執行流程受抽象模板類控制。
四、代碼實現
加入有這樣一個系統,該系統對外提供一系列不同的接口,例如天氣預報系統,對外提供:
1、查詢城市列表
2、查詢某城市天氣
3、…(等等不同性質的接口)
這些接口處理,無一例外都需要遵守相同的處理步驟:
1、驗證來源是否合法
2、解密請求的報文
3、進行對應的業務處理
4、將業務處理返回的對象字符串進行加密
5、字符串進行加密後,再進加簽
6、最後再返回給調用方加簽後的結果
角色 | 類 |
---|---|
抽象模板角色 | AbstractTemplate.java |
具體子類角色 | BusinessA.java、BusinessC.java、BusinessC.java |
測試客戶類 | ClientTest.java |
AbstractTemplate.java
package com.design.demo.behavior.template;
/**
* 接口抽象類
* 現實中的場景往往更復雜,出入參對象也通常不會是String類型
*
* @author administrator
* @date 2020-05-30 22:33
*/
public abstract class AbstractTemplate {
/**
* 入口方法
*
* @param str
* @return
*/
public String handle(String str) {
this.step1(str);//驗證簽名
String plainText = this.step2(str);//解密
String childResStr = this.busiHandle(plainText);//將解密後的報文交給子類去處理,並且得到子類返回的對象
String cipherText = this.step4(childResStr);//加密子類返回的內容
String resStr = this.step5(cipherText);//密文再加上簽名
return resStr;//最後返回給調用方
}
/**
* 對報文進行驗證簽名,檢查來源是否合法
*
* @param str
* @return
*/
private boolean step1(String str) {
//省略具體實現...
System.out.println("對請求對象:[" + str + "]校驗來源是否合法!");
return true;
}
/**
* 對報文解密,得到明文報文
*
* @param str
* @return
*/
private String step2(String str) {
//省略具體實現...
System.out.println("對請求對象:[" + str + "]進行解密!");
String plainText = "明文" + str;
return plainText;
}
/**
* 對解密後的報文,進行業務處理,得到返回報文
*
* @param str
* @return
*/
protected abstract String busiHandle(String str);
/**
* 對要返回出去的報文進行加密,得到密文
*
* @param str
* @return
*/
private String step4(String str) {
//省略具體實現...
System.out.println("對返回對象:[" + str + "]進行加密!");
return str;
}
/**
* 對密文進行加簽,得到含有簽名的密文
*
* @param str
* @return
*/
private String step5(String str) {
//省略具體實現...
System.out.println("對返回對象:[" + str + "]進行加簽名!");
return str;
}
}
BusinessA.java
package com.design.demo.behavior.template;
/**
* 遵守AbstractTemplate的其中一種業務實現
*
* @author administrator
* @date 2020-05-30 22:40
*/
public class BusinessA extends AbstractTemplate {
@Override
protected String busiHandle(String str) {
//我只需要做好關於BusinessA的實現就行了,其他相關的都是由父類去統籌
//省略具體實現...
String resStr = "BusinessA";
System.out.println("關於BusinessA的實現,入參內容:[" + str + "]出參內容:[" + resStr + "]");
return resStr;
}
}
BusinessB.java
package com.design.demo.behavior.template;
/**
* 遵守AbstractTemplate的其中一種業務實現
* @author administrator
* @date 2020-05-30 22:40
*/
public class BusinessB extends AbstractTemplate {
@Override
protected String busiHandle(String str) {
//我只需要做好關於BusinessA的實現就行了,其他相關的都是由父類去統籌
//省略具體實現...
String resStr = "BusinessB";
System.out.println("關於BusinessB的實現,入參內容:[" + str + "]出參內容:[" + resStr + "]");
return resStr;
}
}
BusinessC.java
package com.design.demo.behavior.template;
/**
* 遵守AbstractTemplate的其中一種業務實現
* @author administrator
* @date 2020-05-30 22:40
*/
public class BusinessC extends AbstractTemplate {
@Override
protected String busiHandle(String str) {
//我只需要做好關於BusinessA的實現就行了,其他相關的都是由父類去統籌
//省略具體實現...
String resStr = "BusinessC";
System.out.println("關於BusinessC的實現,入參內容:[" + str + "]出參內容:[" + resStr + "]");
return resStr;
}
}
ClientTest.java
package com.design.demo.behavior.template;
/**
* @author administrator
* @date 2020-05-30 22:55
*/
public class ClientTest {
public static void main(String[] args) {
String str1 = "業務1";
AbstractTemplate at1 = new BusinessA();
at1.handle(str1);
System.out.println("------------------------------");
String str2 = "業務2";
AbstractTemplate at2 = new BusinessB();
at2.handle(str2);
System.out.println("------------------------------");
String str3 = "業務3";
AbstractTemplate at3 = new BusinessC();
at3.handle(str3);
}
}
測試類運行結果