Java設計模式——命令模式
阿新 • • 發佈:2019-01-02
概述
命令模式是把“請求動作或操作”封裝成一個“命令物件”,“呼叫者” 通過該 “命令物件” 把 “命令” 傳送到 “接收者” 執行 “操作”。(看不懂沒關係,我的文字表達水平比較一般,看例子很容易明白了)
例子
舉一個來自《Head First設計模式》的例子:“在餐廳點餐”
場景:顧客到餐廳點餐,寫選單給服務員,服務員把選單給廚師,廚師按照選單要求做菜。 人物:顧客(發起者)、服務員(呼叫者)、廚師(接收者)。 分析:在大家日常點餐可以知道,顧客與廚師是被隔離的,顧客只管點餐不需要知道菜是如何炒的細節,廚師只管做菜執行命令,互不影響。這跟“命令模式”的目的很一致,把命令的“發起者”和“接收/執行者”獨立起來,實現解耦。
再舉一個更貼近生活的例子:
客戶(發起人):balabala提要求(命令)
需求哥(排程者):哦哦哦哦哦地記下一條又一條的需求(命令)
然後,需求哥把一條條的需求發給你(程式碼搬運工)
你(接收/執行者):這需求不可能實現,沒法做~~~
需求哥:這是客戶要求,可以不做,不過鍋你背,工資你扣
客戶提出要求後不需要理會內部如何實現,而你~~~~
凌晨2點,客戶在床上papapa,你在鍵盤上papapa
類圖
程式碼
//命令介面
public interface Command {
public void setReceiver(Receiver receiver);
public void execute();
}
//實現介面的具體命令
public class UiCommand implements Command {
private Receiver receiver;
@Override
public void setReceiver(Receiver receiver) {
this.receiver = receiver;
}
@Override
public void execute() {
receiver.talk();
receiver.execute();
}
}
//接收者(碼農)
public class Receiver {
public void talk() {
System.out.println("討論需求...");
}
public void execute() {
System.out.println("開始幹活....");
this.thinking();
this.doing();
this.extraWork();
this.end();
}
private void thinking() {
System.out.println("思考解決方案.....");
}
private void doing() {
System.out.println("開始寫程式碼......");
}
private void extraWork() {
System.out.println("加班寫程式碼.........");
}
private void end() {
System.out.println("");
System.out.println("享年28....");
}
}
//呼叫者(需求人員)
public class RequireInvoker {
private Command command;
public void setCommand(Command command){
this.command = command;
}
public void execute() {
command.execute();
}
}
//客戶爸爸
public class Customer {
public static void main(String[] args) {
//內部明確好分工,哪個程式設計師負責UI,哪個負責資料優化
//先建立個接收者物件
Receiver receiver = new Receiver();
//再建立個命令物件
Command command = new UiCommand();
//指定命令的接收者
command.setReceiver(receiver);
//建立個呼叫者物件
RequireInvoker invoker = new RequireInvoker();
//客戶把要求給需求人員
invoker.setCommand(command);
//開始幹活吧
invoker.execute();
}
}
輸出結果:
命令模式特點:
1.和所有設計模式特點差不多,解耦。“命令者”與“接收者”隔離。新增命令不用改原始碼。
2.把“具體行為或操作”封裝成一個具體的物件,比如說客戶口述的需求也是命令。
3.這個設計模式可以輕易設計成,巨集命令(能批量執行命令的命令),Head First上面有講,其實很容易理解,口述一下吧,建立一個巨集命令(同樣實現Command介面),然後把其他命令add()進去,在它的execute()裡面遍歷並執行所有的命令。
4.可以記錄所有執行過的命令。在Invoker類里加上個ArrayList,每執行一次命令就add()一下或者可以直接寫入到硬盤裡,系統掛掉了也能按記錄重新執行。
第3、4點可以用於訊息佇列、日誌系統