java命令_JAVA与模式之命令模式
在閻宏博士的《JAVA與模式》一書中開頭是這樣描述命令(Command)模式的:
命令模式屬于對象的行為模式。命令模式又稱為行動(Action)模式或交易(Transaction)模式。
命令模式把一個請求或者操作封裝到一個對象中。命令模式允許系統使用不同的請求把客戶端參數化,對請求排隊或者記錄請求日志,可以提供命令的撤銷和恢復功能。
命令模式的結構
命令模式是對命令的封裝。命令模式把發出命令的責任和執行命令的責任分割開,委派給不同的對象。
每一個命令都是一個操作:請求的一方發出請求要求執行一個操作;接收的一方收到請求,并執行操作。命令模式允許請求的一方和接收的一方獨立開來,使得請求的一方不必知道接收請求的一方的接口,更不必知道請求是怎么被接收,以及操作是否被執行、何時被執行,以及是怎么被執行的。
命令允許請求的一方和接收請求的一方能夠獨立演化,從而具有以下的優點:
命令模式使新的命令很容易地被加入到系統里。
允許接收請求的一方決定是否要否決請求。
能較容易地設計一個命令隊列。
可以容易地實現對請求的撤銷和恢復。
在需要的情況下,可以較容易地將命令記入日志。
下面以一個示意性的系統,說明命令模式的結構。
命令模式涉及到五個角色,它們分別是:
客戶端(Client)角色:創建一個具體命令(ConcreteCommand)對象并確定其接收者。
命令(Command)角色:聲明了一個給所有具體命令類的抽象接口。
具體命令(ConcreteCommand)角色:定義一個接收者和行為之間的弱耦合;實現execute()方法,負責調用接收者的相應操作。execute()方法通常叫做執行方法。
請求者(Invoker)角色:負責調用命令對象執行請求,相關的方法叫做行動方法。
接收者(Receiver)角色:負責具體實施和執行一個請求。任何一個類都可以成為接收者,實施和執行請求的方法叫做行動方法。
源代碼
接收者角色類
1public?class?Receiver?{2????/**3?????*?真正執行命令相應的操作4?????*/
5????public?void?action(){
6????????System.out.println("執行操作");
7????}
8}
抽象命令角色類
1public?interface?Command?{2????/**3?????*?執行方法4?????*/
5????void?execute();
6}
具體命令角色類
1public?class?ConcreteCommand?implements?Command?{2????//持有相應的接收者對象
3????private?Receiver?receiver?=?null;
4????/** 5?????*?構造方法 6?????*/
7????public?ConcreteCommand(Receiver?receiver){
8????????this.receiver?=?receiver;
9????}
10????@Override
11????public?void?execute()?{
12????????//通常會轉調接收者對象的相應方法,讓接收者來真正執行功能
13????????receiver.action();
14????}
15
16}
請求者角色類
1public?class?Invoker?{2????/** 3?????*?持有命令對象 4?????*/
5????private?Command?command?=?null;
6????/** 7?????*?構造方法 8?????*/
9????public?Invoker(Command?command){
10????????this.command?=?command;
11????}
12????/**13?????*?行動方法14?????*/
15????public?void?action(){
16
17????????command.execute();
18????}
19}
客戶端角色類
1public?class?Client?{2
3????public?static?void?main(String[]?args)?{
4????????//創建接收者
5????????Receiver?receiver?=?new?Receiver();
6????????//創建命令對象,設定它的接收者
7????????Command?command?=?new?ConcreteCommand(receiver);
8????????//創建請求者,把命令對象設置進去
9????????Invoker?invoker?=?new?Invoker(command);
10????????//執行方法
11????????invoker.action();
12????}
13
14}
AudioPlayer系統
小女孩茱麗(Julia)有一個盒式錄音機,此錄音機有播音(Play)、倒帶(Rewind)和停止(Stop)功能,錄音機的鍵盤便是請求者(Invoker)角色;茱麗(Julia)是客戶端角色,而錄音機便是接收者角色。Command類扮演抽象命令角色,而PlayCommand、StopCommand和RewindCommand便是具體命令類。茱麗(Julia)不需要知道播音(play)、倒帶(rewind)和停止(stop)功能是怎么具體執行的,這些命令執行的細節全都由鍵盤(Keypad)具體實施。茱麗(Julia)只需要在鍵盤上按下相應的鍵便可以了。
錄音機是典型的命令模式。錄音機按鍵把客戶端與錄音機的操作細節分割開來。
源代碼
接收者角色,由錄音機類扮演
1public?class?AudioPlayer?{2
3????public?void?play(){
4????????System.out.println("播放...");
5????}
6
7????public?void?rewind(){
8????????System.out.println("倒帶...");
9????}
10
11????public?void?stop(){
12????????System.out.println("停止...");
13????}
14}
抽象命令角色類
1public?interface?Command?{2????/**3?????*?執行方法4?????*/
5????public?void?execute();
6}
具體命令角色類
1public?class?PlayCommand?implements?Command?{2
3????private?AudioPlayer?myAudio;
4
5????public?PlayCommand(AudioPlayer?audioPlayer){
6????????myAudio?=?audioPlayer;
7????}
8????/** 9?????*?執行方法10?????*/
11????@Override
12????public?void?execute()?{
13????????myAudio.play();
14????}
15
16}
1public?class?RewindCommand?implements?Command?{
2
3????private?AudioPlayer?myAudio;
4
5????public?RewindCommand(AudioPlayer?audioPlayer){
6????????myAudio?=?audioPlayer;
7????}
8????@Override
9????public?void?execute()?{
10????????myAudio.rewind();
11????}
12
13}
1public?class?StopCommand?implements?Command?{
2????private?AudioPlayer?myAudio;
3
4????public?StopCommand(AudioPlayer?audioPlayer){
5????????myAudio?=?audioPlayer;
6????}
7????@Override
8????public?void?execute()?{
9????????myAudio.stop();
10????}
11
12}
請求者角色,由鍵盤類扮演
1public?class?Keypad?{2????private?Command?playCommand;
3????private?Command?rewindCommand;
4????private?Command?stopCommand;
5
6????public?void?setPlayCommand(Command?playCommand)?{
7????????this.playCommand?=?playCommand;
8????}
9????public?void?setRewindCommand(Command?rewindCommand)?{
10????????this.rewindCommand?=?rewindCommand;
11????}
12????public?void?setStopCommand(Command?stopCommand)?{
13????????this.stopCommand?=?stopCommand;
14????}
15????/**16?????*?執行播放方法17?????*/
18????public?void?play(){
19????????playCommand.execute();
20????}
21????/**22?????*?執行倒帶方法23?????*/
24????public?void?rewind(){
25????????rewindCommand.execute();
26????}
27????/**28?????*?執行播放方法29?????*/
30????public?void?stop(){
31????????stopCommand.execute();
32????}
33}
客戶端角色,由茱麗小女孩扮演
1public?class?Julia?{2????public?static?void?main(String[]args){
3????????//創建接收者對象
4????????AudioPlayer?audioPlayer?=?new?AudioPlayer();
5????????//創建命令對象
6????????Command?playCommand?=?new?PlayCommand(audioPlayer);
7????????Command?rewindCommand?=?new?RewindCommand(audioPlayer);
8????????Command?stopCommand?=?new?StopCommand(audioPlayer);
9????????//創建請求者對象
10????????Keypad?keypad?=?new?Keypad();
11????????keypad.setPlayCommand(playCommand);
12????????keypad.setRewindCommand(rewindCommand);
13????????keypad.setStopCommand(stopCommand);
14????????//測試
15????????keypad.play();
16????????keypad.rewind();
17????????keypad.stop();
18????????keypad.play();
19????????keypad.stop();
20????}
21}
運行結果如下:
宏命令
所謂宏命令簡單點說就是包含多個命令的命令,是一個命令的組合。
設想茱麗的錄音機有一個記錄功能,可以把一個一個的命令記錄下來,再在任何需要的時候重新把這些記錄下來的命令一次性執行,這就是所謂的宏命令集功能。因此,茱麗的錄音機系統現在有四個鍵,分別為播音、倒帶、停止和宏命令功能。此時系統的設計與前面的設計相比有所增強,主要體現在Julia類現在有了一個新方法,用以操作宏命令鍵。
源代碼
系統需要一個代表宏命令的接口,以定義出具體宏命令所需要的接口。
1public?interface?MacroCommand?extends?Command?{2????/** 3?????*?宏命令聚集的管理方法 4?????*?可以添加一個成員命令 5?????*/
6????public?void?add(Command?cmd);
7????/** 8?????*?宏命令聚集的管理方法 9?????*?可以刪除一個成員命令10?????*/
11????public?void?remove(Command?cmd);
12}
具體的宏命令MacroAudioCommand類負責把個別的命令合成宏命令。
1public?class?MacroAudioCommand?implements?MacroCommand?{2
3????private?List?commandList?=?new?ArrayList(); 4????/** 5?????*?宏命令聚集管理方法 6?????*/ 7????@Override 8????public?void?add(Command?cmd)?{ 9????????commandList.add(cmd);10????}11????/**12?????*?宏命令聚集管理方法13?????*/14????@Override15????public?void?remove(Command?cmd)?{16????????commandList.remove(cmd);17????}18????/**19?????*?執行方法20?????*/21????@Override22????public?void?execute()?{23????????for(Command?cmd?:?commandList){24????????????cmd.execute();25????????}26????}2728}
客戶端類Julia
1public?class?Julia?{2
3????public?static?void?main(String[]args){
4????????//創建接收者對象
5????????AudioPlayer?audioPlayer?=?new?AudioPlayer();
6????????//創建命令對象
7????????Command?playCommand?=?new?PlayCommand(audioPlayer);
8????????Command?rewindCommand?=?new?RewindCommand(audioPlayer);
9????????Command?stopCommand?=?new?StopCommand(audioPlayer);
10
11????????MacroCommand?marco?=?new?MacroAudioCommand();
12
13????????marco.add(playCommand);
14????????marco.add(rewindCommand);
15????????marco.add(stopCommand);
16????????marco.execute();
17????}
18}
運行結果如下:
命令模式的優點
更松散的耦合
命令模式使得發起命令的對象——客戶端,和具體實現命令的對象——接收者對象完全解耦,也就是說發起命令的對象完全不知道具體實現對象是誰,也不知道如何實現。更動態的控制
命令模式把請求封裝起來,可以動態地對它進行參數化、隊列化和日志化等操作,從而使得系統更靈活。很自然的復合命令
命令模式中的命令對象能夠很容易地組合成復合命令,也就是宏命令,從而使系統操作更簡單,功能更強大。更好的擴展性
由于發起命令的對象和具體的實現完全解耦,因此擴展新的命令就很容易,只需要實現新的命令對象,然后在裝配的時候,把具體的實現對象設置到命令對象中,然后就可以使用這個命令對象,已有的實現完全不用變化。
轉載于:https://www.cnblogs.com/java-my-life/archive/2012/06/01/2526972.html
總結
以上是生活随笔為你收集整理的java命令_JAVA与模式之命令模式的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 鸡蛋股票代码
- 下一篇: 链表的数据域怎么使用结构体_一步一步教你