java命令模式


意圖:將一個請求封裝為一個對象,從而可用不同的請求對客戶進行參數化;對請求排隊或記錄日志,以及支持可撤銷的操作
動機:將”發出請求的對象”和”接收與執行這些請求的對象”分隔開來。
效果:
1)、command模式將調用操作的對象和實現該操作的對象解耦
2)、可以將多個命令裝配成一個復合命令,復合命令是Composite模式的一個實例
3)、增加新的command很容易,無需改變已有的類
適用性:
1)、抽象出待執行的動作以參數化某對象
2)、在不同的時刻指定、排列和執行請求。如請求隊列
3)、支持取消操作
4)、支持修改日志
5)、用構建在原語操作上的高層操作構造一個系統。支持事物
參與者:
1)、Command
  聲明執行操作的接口
2)、ConcreteCommand
  將一個接收者對象綁定於一個動作
  調用接收者相應的操作,以實現execute
3)、Client
  創建一個具體命令對象並設定它的接收者
4)、Invoker
  要求該命令執行這個請求
5)、Receiver
  知道如何實施與執行一個請求相關的操作。任何類都可能作為一個接收者
結構圖:

協作:
1)、client創建一個ConcreteCommand對象並指定它的Receiver對象
2)、某Invoker對象存儲該ConcreteCommand對象
3)、該Invoker通過調用Command對象的execute操作來提交一個請求。若該命令是可撤銷的,ConcreteCommand在執行execute操作前存儲當前狀態以用於取消該命令
4)、ConcreteCommand對象調用它的Receiver的操作以執行該請求
命令對象將動作和接受者包進對象中,這個對象只暴露出一個execute()方法,當此方法被調用的時候,接收者就會進行這些動作。從外面來看,其他對象不知道究竟哪個接收者進行了哪些動作,只知道如果調用execute()方法,請求的目的就能達到。 

實例:

 1 package com.test.patten.command;
 2 
 3 /**
 4  * 命令接口
 5  */
 6 public interface Command {
 7     /**
 8      * 執行命令
 9      */
10     public void execute();
11     /**
12      * 撤銷命令
13      */
14     public void undo();
15 }
 1 package com.test.patten.command;
 2 
 3 /**
 4  * 命令
 5  */
 6 public class CreateCommand implements Command{
 7     private Receiver receiver;
 8     private String state;
 9     
10     public CreateCommand(Receiver receiver){
11         this.receiver = receiver;
12     }
13 
14     @Override
15     public void execute() {
16         receiver.action();
17     }
18 
19     @Override
20     public void undo() {
21         receiver.unAction();
22     }
23     
24 }
 1 package com.test.patten.command;
 2 
 3 /**
 4  * 命令接收者,命令真正執行人
 5  */
 6 public class Receiver {
 7     public void action(){
 8         System.out.println("執行命令...");
 9     }
10     
11     public void unAction(){
12         System.out.println("撤銷命令...");
13     }
14 }
 1 package com.test.patten.command;
 2 
 3 public class Invoker {
 4     /**
 5      * 調用者持有命令對象
 6      */
 7     private Command command;
 8 
 9     /**
10      * 設置命令對象
11      * @param command
12      */
13     public void setCommand(Command command) {
14         this.command = command;
15     }
16     public Command getCommand() {
17         return command;
18     }
19 
20     /**
21      * 執行命令
22      */
23     public void runCommand(){
24         command.execute();
25     }
26     /**
27      * 撤銷命令
28      */
29     public void unDoCommand(){
30         command.undo();
31     }
32 }
 1 package com.test.patten.command;
 2 
 3 public class Client {
 4     public static void main(String[] args){
 5         //創建接受者
 6         Receiver receiver = new Receiver();
 7         //創建命令對象,並設置它的接受者
 8         Command command = new CreateCommand(receiver);
 9         
10         //創建調用者,將命令對象設置進去
11         Invoker invoker = new Invoker();
12         invoker.setCommand(command);
13         
14         //這里可以測試一下
15         invoker.runCommand();
16         invoker.unDoCommand();
17     }
18 }

常見應用:
1、工作隊列,線程池,日程安排
2、日志請求(系統恢復)
要點:
1、命令模式將發出請求的對象和執行請求的對象解耦
2、在被解耦的兩者之間是通過命令對象進行溝通的。命令對象封裝了接收者和一個或一組動作
3、調用者通過調用命令對象的execute()發出請求,這會使得接收者的動作被調用
4、調用者可以接受命令當作參數,甚至在運行時動態的進行
5、命令可以支持撤銷,做法是實現一個undo()方法來回到execute()被執行前的狀態
6、宏命令是命令的一種簡單的延伸,允許調用多個命令。宏方法也可以支持撤銷
7、實際操作時,很常見使用"聰明"命令對象,也就是直接實現了請求,而不是將工作委托給接受者(弊端?)
8、命令也可以用來實現日志和事物系統


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM