设计模式-行为模式(Command)

原创 2005年05月23日 15:45:00

设计模式-行为模式(Command)

1、  定义:

把请求封装成一个可重用的对象,对于每次请求,这些对象的行为都可以被参数化。并且支持可取消的操作。

《设计模式的有趣解释-追MM》中解释:Command—俺有一个mm家里管得特别严,没法见面,只好借助于她弟弟在我们俩之间传送信息,她对我有什么指示,就写一张纸条让她弟弟带给我。这不,她弟弟又传送过来一个command,为了感谢他,我请他吃了碗杂酱面,哪知道他说:我同时给我姐姐三个男朋友送command,就数你最小气,才请我吃面。

      命令模式:命令模式把一个请求或者操作封装到一个对象中。命令模式把发出命令的责任和执行命令的责任分割开,委派给不同的对象。命令模式允许请求的一方和发送的一方独 立开来,使得请求的一方不必知道接收请求的一方的接口,更不必知道请求是怎么被接收 ,以及操作是否执行,何时被执行以及是怎么被执行的。系统支持命令的撤消。

这是Command模式的UML图:

2、  适用性:

JAVASWING的组件中对Command模式的运用非常多,像菜单(MenuItem)对象那样,抽象出待执行的动作以参数化某对象。你可用过程语言中的回调(Callback)函数表达这种参数化机制。所谓回调函数是指函数先在某处注册,而它将在稍后某个需要的时候被调用。Command 模式是回调机制的一个面向对象的替代品。

在不同的时刻指定、排列和执行请求。一个Command 对象可以有一个与初始请求无关的生存期。如果一个请求的接收者可用一种与地址空间无关的方式表达,那么就可将负责该请求的命令对象传送给另一个不同的进程并在那儿实现该请求。

支持取消操作。Command Excecute操作可在实施操作前将状态存储起来,在取消操作时这个状态用来消除该操作的影响。Command 接口必须添加一个UnExcecute 操作,该操作取消上一次Excecute 调用的效果。执行的命令被存储在一个历史列表中。可通过向后和向前遍历这一列表并分别调用UnExcecute Excecute 来实现重数不限的取消重做

支持修改日志,这样当系统崩溃时,这些修改可以被重做一遍。在Command 接口中添加装载操作和存储操作,可以用来保持变动的一个一致的修改日志。从崩溃中恢复的过程包括从磁盘中重新读入记录下来的命令并用Excecute 操作重新执行它们。

用构建在原语操作上的高层操作构造一个系统。这样一种结构在支持事务( transaction)的信息系统中很常见。一个事务封装了对数据的一组变动。Command 模式提供了对事务进行建模的方法。Command 有一个公共的接口,使得你可以用同一种方式调用所有的事务。同时使用该模式也易于添加新事务以扩展系统。

3、  经典应用

Struts中的Action的设计就采用了这个模式:
    protected ActionForward
        processActionPerform(HttpServletRequest request, HttpServletResponse response, Action action, ActionForm form, ActionMapping mapping) throws IOException, ServletException {
        try {
            return (action.execute(mapping, form, request, response));
        } catch (Exception e) {
            return (processException(request, response, e, form, mapping));
        }
    }
    Action
是一个接口,每一个实现它的对象都必须实现execute方法,在执行这个函数之前,已经通过Action action = processActionCreate(request, response, mapping);得到客户端所请求的action对象。客户端通过login.do形式发送给ActionServlet,就可以调用LoginAction对象,通过search.do的形式就能调用SearchAction对象,而ActionServlet不用知道客户端发送的是什么请求。

4、  经典实现-用Command的模式实现Redo/Undo功能

设计了如下一个通用接口(封装用户请求的命令):
public Interface Command
{      

//执行用户当前指令,比如(copypastecutdelete)等
public void execute();

//返回上一操作
public void undo();

//返回下一操作
public void redo();

}

设计一个管理用户操作指令的接口CommandManager(管理用户所有的操作,以便支持取消操作):
public Interface CommandManager
{

//保存用户操作的指令
      public void storeCommand(Command cmd);

//清除用户所有操作指令
      public void clearAllCommand();

//返回用户上一操作
      public void undo();

//返回用户下一操作
      public void redo();
}

现在来实现一个用户命令:
public class DeleteCommand implements Command
{

    public void execute()
    {
        /*
备份上次操作后数据数据 */
        /*
执行用户新的指令(删除、粘贴等操作) */

    }

public void undo()
    {
         /* 
返回用户上次的数据  */
    }

public void redo()
    {
         /* 
返回用户下次的数据  */
    }

}

这样的话我们每做一个编辑动作,就执行一个相应的command.接下来我们要考虑如何将这些执行过的命令保存下来,以实现undo/redo

public class CommandHistoryManager implements CommandManager
{
 Vector undoList=new Vector();
 Vector redoList=new Vector();
 
 public void storeCommand(Command cmd)
 {
  undoList.add(cmd);
 }
 public void clearAllCommand()
 {
  undoList.clear();
  redoList.clear();
 }
 public void undo()
 {
        if ( undoList.size() <= 0 ) return;
        Command cmd = ((Command)(undoList.get(undoList.size()-1)));
        cmd.undo();
        undoList.remove(cmd);
        redoList.add(cmd);
 }
 public void redo()
 {
        if ( redoList.size() <= 0 ) return;
        Command cmd = ((Command)(redoList.get(redoList.size()-1)));
        cmd.execute();
        redoList.remove(cmd);
        undoList.add(cmd);
 }
}

通过storeCommand()方法,每次执行的command就可以保存到undoList中,假设再在我们在程序中放置了两个按钮,一个undo,一个redo.按下undo按钮,就执行CommandHistoryManager的undo()方法,undo()方法会调用undoList中保存的最后一个command的undo()方法,并将这个command再放到redoList中,最后从undoList中删除这个命令。这时如果再按redo按钮,它会调用CommandHistoryManager中的redo()方法。redo()方法会调用redoList中保存的最后一个command的execute()方法,并将这个command又存回到undoList中。这样就实现了无限次数的undo/redo功能。

参考:http://www.csdn.com.cn/program/2769.htm

设计模式(1)-创建模式、结构模式、行为模式的区别

创建模式 创建型模式,就是创建对象的模式,抽象了实例化的过程。 它帮助一个系统独立于如何创建、组合和表示它的那些对象。 关注的是对象的创建,创建型模式将创建对象的过程进行了抽象,也可以理解为将创建...
  • qq_29994609
  • qq_29994609
  • 2016年07月15日 00:14
  • 1765

23种设计模式分析(5):行为型模式

1.1.13 Observer观察者模式   Observer(观察者)模式又被称作发布-订阅(Publish-Subscribe)模式,是一种对象的行为型模式。《设计模式》一书对Observer...
  • zhoudaxia
  • zhoudaxia
  • 2014年04月06日 23:21
  • 4968

Java经典设计模式之十一种行为型模式(附实例和详解)

Java经典设计模式共有21中,分为三大类:创建型模式(5种)、结构型模式(7种)和行为型模式(11种)。本文主要讲行为型模式,创建型模式和结构型模式可以看博主的另外两篇文章:Java经典设计模式之五...
  • u013142781
  • u013142781
  • 2016年03月08日 20:06
  • 7498

Java经典23种设计模式之行为型模式(一)

行为型设计模式有11种,分别是
  • yanzi1225627
  • yanzi1225627
  • 2014年07月13日 10:43
  • 2526

erlang项目常见OTP行为模式

最近学习erlang有一些眉目了。在使用OTP进行erlang项目开发时,会遇到很多OTP的行为模式。而这种行为模式,有一些像面像对象中的设计模式。了解了这些东西,可以更好的使用OTP库进行erlan...
  • fengmm521
  • fengmm521
  • 2017年11月03日 18:54
  • 149

java设计模式之行为模型模式

前面学习了创造模式系列和结构模式系列,本文来学习下行为模式系列 这一章打算找一些开源项目中的代码例子来写。 父类与子类 策略模式 针对接口的一个方法有不同的实现,让客户来选择 模板方法...
  • akfly
  • akfly
  • 2017年01月23日 18:33
  • 334

设计模式-行为模式之Command

Command(命令)是一种行为模式,让你可以把请求转换到单独的对象,可以用来把不同的请求参数化,排队或者记录请求,并且支持撤销操作。问题假设你在做一个新的文本编辑器。你创建了一个Button类,可以...
  • myjcxd
  • myjcxd
  • 2017年12月26日 22:41
  • 61

(行为模式)设计模式之Command

Command定义 不少Command模式的代码都是针对图形界面的,它实际就是菜单命令,我们在一个下拉菜单选择一个命令时,然后会执行一些动作. 将这些命令封装成在一个类中,然后用户(调用者)再对这个类...
  • pein
  • pein
  • 2006年05月13日 10:48
  • 534

设计模式分类(创建型模式、结构型模式、行为模式)

1.创建型模式 前面讲过,社会化的分工越来越细,自然在软件设计方面也是如此,因此对象的创建和对象的使用分开也就成为了必然趋势。因为对象的创建会消耗掉系统的很多资源,所以单独对对象的创建进行研究,从而能...
  • itpinpai
  • itpinpai
  • 2016年04月25日 18:51
  • 8149

创建模式、结构模式、行为模式的区别

创建模式 创建型模式,就是创建对象的模式,抽象了实例化的过程。  它帮助一个系统独立于如何创建、组合和表示它的那些对象。  关注的是对象的创建,创建型模式将创建对象的过程进行了抽象,也可...
  • AlbertFly
  • AlbertFly
  • 2016年08月22日 16:37
  • 1109
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:设计模式-行为模式(Command)
举报原因:
原因补充:

(最多只允许输入30个字)