将请求封装为对象,从而可以使用不同的请求对客户进行参数化,该模式的关键在于对不同请求的封装。简单的说,也就是在请求发出者和客户间通过command对象进行解耦,从而使得请求者可以通过实例化不同的command对象实现不同操作。
command模式类似于c++的回调,我们需要在command的实现类中注册回调函数,也就是将命令的具体执行者注册。
在GOF中,使用了Menu,MenuItem以及doucment的例子还阐述command模式。用户点击menu,将操作事件委托给MenuItem,不同的MenuItem拥有不同的concreteCommand,从而实现menuItem与操作执行者的解耦。
另外,command模式可以支持复合操作,也就是执行一批command(接口实现缘故),并且可以通过记录操作前状态实现撤销操作unexecute,从而为事务处理提供了基础。
command模式的效果:
1) command模式将调用操作的对象与知道如何实现该操作的对象解耦
2) command对象可以像其他对象一样被操纵和扩展
3) 多个command可以复合
4) 增加新command很容易,无需改变其他类
给个例子:
还是公司的事情,公司里有一位大boss;他不喜欢见人,可能是长得丑,也可能是其他原因。他的任何命令都是通过写在小纸条上的command来执行的。纸条上会写上需要执行的任务。如boss想要开房,他就下发一道开房command。
另外一个部门负责编写不同的小纸条,并决定由谁去给boss开房,有可能是大泽玛利亚,也有可能是uncle wang,当然这就跟boss没有关系了,反正房开好了就可以。
这样,就实现了boss和秘书之间的解耦。
代码:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19 |
package
com.inspur.jiyq.designpattern.command; import com.inspur.jiyq.designpattern.command.impl.ReserveCommand; import com.inspur.jiyq.designpattern.command.impl.SendMessageCommand; public class BossMain { public
static void main(String[] args) { //通过使用command模式,实现了boss和秘书的解耦 //boss想发邮件 Command mailCommand = new
SendMessageCommand( new
MailMan()); mailCommand.execute(); //boss想开房 Command reserveCommand = new
ReserveCommand( new
Secretary()); reserveCommand.execute(); } } |
1
2
3
4
5
6
7
8
9
10
11
12
13 |
package
com.inspur.jiyq.designpattern.command; public interface Command { /** * 执行命令 */ public
void execute(); /** * 取消已经执行的命令 */ public
void unexecute(); } |
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19 |
package
com.inspur.jiyq.designpattern.command; public class MailMan { /** * 发邮件 */ public
void sendMail() { System.out.println( "MailMan sending mails." ); } /** * 回收邮件,前提是得保存前一次送件地址 */ public
void retrieve() { System.out.println( "MailMan retrieve mails" ); } } |
1
2
3
4
5
6
7
8
9
10
11 |
package
com.inspur.jiyq.designpattern.command; public class Secretary { /** * 秘书需要做各种预定 */ public
void reserve() { System.out.println( "Secretary book a room." ); } } |
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24 |
package
com.inspur.jiyq.designpattern.command.impl; import com.inspur.jiyq.designpattern.command.Command; import com.inspur.jiyq.designpattern.command.Secretary; public class ReserveCommand implements
Command{ private
Secretary secretary; public
ReserveCommand(Secretary secretary) { this .secretary = secretary; } @Override public
void execute() { secretary.reserve(); } @Override public
void unexecute() { // TODO Auto-generated method stub } } |
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29 |
package
com.inspur.jiyq.designpattern.command.impl; import com.inspur.jiyq.designpattern.command.Command; import com.inspur.jiyq.designpattern.command.MailMan; public class SendMessageCommand implements
Command { /** * 快递哥 */ private
MailMan mailMan; public
SendMessageCommand(MailMan mailMan) { this .mailMan = mailMan; } @Override public
void execute() { mailMan.sendMail(); } @Override public
void unexecute() { //如果送出去的信写错了,可以要求信差收回来,前提是信差可以这么做 } } |
原文:http://www.cnblogs.com/jiyuqi/p/3670812.html