在.Net框架中很多对象的方法中都会有Invoke方法,这种方法的设计实际是用了设计模式的命令模式,

模式图如下

其核心思路是将Client 向Receiver发送的命令行为进行抽象(ICommand),实例化(ConcreteCommand),以便对这些行为能够控制(记录,取消,恢复);

每个Command与Client是解耦的,即不依赖具体客户,调度者Invoker可以负责记录,控制客户执行了那些请求,与客户端存在单一的关联。

示例:计算器(Calculator)可以执行很多计算操作,客户(client)向指定的接收者发送指令,命令从客户到达接收者实际上是间接进行的,是先通过调度者(Invoker)将指定的输入(state)和指定的命令,传递给接收者,接受者再执行具体的任务。代码如下

//示例:一个计算器,接受用户的计算请求,计算器提供一些计算方法,要求请求任务中过程可以记录请求的行为,请求中状态的变化和请求继续和取消
public class Client
{
public Invoker Invoker { get; set; } = new Invoker();
//简化代码
public void Invoke(string CommandName,params object[] states)
{
Invoker.Invoke(CommandName, states);
}
//简化代码
public void Invoke(string CommandName,out object result,params object[] states)
{
Invoker.Invoke(CommandName, out result, states);
} } public class Invoker
{
public Dictionary<string, ICommand> Commands { get; set; } = new Dictionary<string, ICommand>(); /// <summary>
///
/// </summary>
/// <param name="CommandName"></param>
/// <param name="returnResult">需要返回结果的命令</param>
/// <param name="states"></param>
public void Invoke(string CommandName,out object returnResult, params object[] states)
{
//传递参数
Commands[CommandName].State = states;
//执行操作
Commands[CommandName].Execute();
returnResult = Commands[CommandName].State;
}
/// <summary>
/// 无需返回结果
/// </summary>
/// <param name="CommandName"></param>
/// <param name="states"></param>
public void Invoke(string CommandName,params object[] states)
{
//传递参数
Commands[CommandName].State = states;
//执行操作
Commands[CommandName].Execute();
} //下面可以写一些方法用来恢复数据或记录行为
//可以在Invoke 方法中使用异步方法放入token来中断执行,并将State恢复到原来状态 } public interface ICommand
{
string CommandName { get; set; }
object State { get; set; }//记录状态,可以是数据
void Execute();
}
//求积运算
public class CalcuteMulCommand : ICommand
{
public string CommandName { get ; set ; }
public object State { get ; set ; } private object receiver;
public CalcuteMulCommand(object _receiver)
{
receiver = _receiver;
}
public void Execute()
{ State= ( (Calculator)receiver).Mutiply((int)((object[])State)[], (int)((object[])State)[]);
}
} internal class Calculator
{
public Calculator()
{
}
public double Mutiply(int a,int b)
{
return a * b;
}
} //测试代码

class Test
    {
        static void Main(string[] args)
        {
           
           
            Client client = new Client();
            client.Invoker.Commands.Add("CalcuteMulCommand", new CalcuteMulCommand(new Calculator()));
            object result;
            client.Invoke("CalcuteMulCommand",out result, 5, 2);


Console.WriteLine(result.ToString());
            Console.ReadKey();
        }
    }

 

面向对象设计模式_命令模式(Command)解读的更多相关文章

  1. 设计模式 ( 十三 ) 命令模式Command(对象行为型)

    设计模式 ( 十三 ) 命令模式Command(对象行为型) 1.概述         在软件设计中,我们经常需要向某些对象发送请求,但是并不知道请求的接收者是谁,也不知道被请求的操作是哪个,我们只需 ...

  2. 乐在其中设计模式(C#) - 命令模式(Command Pattern)

    原文:乐在其中设计模式(C#) - 命令模式(Command Pattern) [索引页][源码下载] 乐在其中设计模式(C#) - 命令模式(Command Pattern) 作者:webabcd ...

  3. 二十四种设计模式:命令模式(Command Pattern)

    命令模式(Command Pattern) 介绍将一个请求封装为一个对象,从而使你可用不同的请求对客户进行参数化:对请求排队或记录请求日志,以及支持可取消的操作. 示例有一个Message实体类,某个 ...

  4. 设计模式-15命令模式(Command Pattern)

    1.模式动机 在软件设计中,我们经常需要向某些对象发送请求,但是并不知道请求的接收者是谁,也不知道被请求的操作是哪个,我们只需在程序运行时指定具体的请求接收者即可,此时,可以使用命令模式来进行设计,使 ...

  5. [设计模式] 14 命令模式 Command

    Command 模式通过将请求封装到一个对象(Command)中,并将请求的接受者存放到具体的 ConcreteCommand 类中(Receiver)中,从而实现调用操作的对象和操作的具体实现者之间 ...

  6. 设计模式之命令模式(Command)摘录

    23种GOF设计模式一般分为三大类:创建型模式.结构型模式.行为模式. 创建型模式抽象了实例化过程,它们帮助一个系统独立于怎样创建.组合和表示它的那些对象.一个类创建型模式使用继承改变被实例化的类,而 ...

  7. 大熊君说说JS与设计模式之------命令模式Command

    一,总体概要 1,笔者浅谈 日常生活中,我们在看电视的时候,通过遥控器选择我们喜欢的频道时,此时我们就是客户端的角色,遥控器的按钮相当于客户请求,而具体执行的对象就是命令对象, 命令模式把一个请求或者 ...

  8. java_设计模式_命令模式_Command Pattern(2016-08-09)

    理解还不到位,先窜出来.等过一阵子再看,再理解. 定义:将一个请求封装成一个对象,从而让你使用不同的请求把客户端参数化,对请求排队或者记录请求日志,可以提供命令的撤销和恢复功能. 类型:行为类模式 类 ...

  9. 设计模式 笔记 命令模式 Command

    //---------------------------15/04/25---------------------------- //Conmmand  命令模式----对象行为型模式 /* 1:意 ...

随机推荐

  1. POJ - 1182 食物链 并查集经典

    思路:设r(x)表示节点x与根结点的关系,px表示x的根结点.记录每个节点与其父节点的关系,就能很方便知道每个节点以及和它的父节点的关系. struct node{ int par; //父亲节点 i ...

  2. 算法训练 K好数 数位DP+同余定理

    思路:d(i,j)表示以i开头,长度为j的K好数的个数,转移方程就是 for(int u = 0; u < k; ++u) { int x = abs(i - u); if(x == 1) co ...

  3. 转:彻底搞清referrer和origin

    在http协议中有这两个字段,之前一直隐隐约约的觉得是,一种标记请求来源的方法(的确是),但是更细致的对这两个字段的比较却没有一个清楚的认识. referrer 到底是referer还是referre ...

  4. java 集合框架(十六)Map

    一.概述 Map是一个包含键值对的集合,一个map不能有重复的键(key),而且每个键至多只能对应一个值.Map同Collection一样,它的所有通用实现都会提供一个转换器构造函数,接收一个Map类 ...

  5. [JCIP笔记] (一)多线程的起源

    在很久很久以前,那时的计算机还没有操作系统这种东西,所以只能有一个程序,从头到尾地跑.于是这个程序要负责使用所有的资源,还得响应外部请求.想想这个程序得多复杂啊--为了做成一件事,可能要先把内存啊.I ...

  6. V4L2驱动的移植与应用(一)

    V4L2(video for linux) 可以支持多种设备,它可以有以下5种接口: 1.视频采集接口(video capture interface):这种应用的设备可以是高频头或者摄像头.V4L2 ...

  7. Android 插件化方案(动态加载)总结

    1.作用 大多数Android开发人员开始接触这个问题是因为 App 爆棚了,方法数超过了一个 Dex 最大方法数 65535 的上限,因而便有了插件化的概念,将一个 App 划分为多个插件(Apk ...

  8. java.sql.SQLException: Access denied for user 'sa'@'localhost' (using password: NO)

    1.错误描述 INFO:2015-05-01 16:53:29[main] - HHH000228: Running hbm2ddl schema update INFO:2015-05-01 16: ...

  9. 用vlc搭建简单流媒体服务器(UDP和TCP方式)

    .UDP(legacy)传统模式 .RTP方式 .RTSP方式 RTSP方式是通过RTP进行流媒体数据的传输的,VLC的实现也是基于UDP的.这种方式网上的参考资料比较多,我就不截图了,直接叙述命令行 ...

  10. ubuntu14.04 64位 安装JDK1.7

    ubuntu14.04 64位 安装JDK1.7 1 新建文件夹 youhaidong@youhaidong:~$ sudo mkdir /usr/lib/jvm 2 解压文件 youhaidong@ ...