命令模式

介绍

命令模式(Command):将一个请求封装为一个对象,从而使你可用不同的请求对客户进行参数化;对请求排队或记录请求日志,以及支持可撤销的操作。

结构图


角色

Receive接收者角色

该角色就是干活的角色,命令传递到这里是应该被执行的。

Command命令角色

需要执行的所有的调用者角色

Invoker调用者角色

接收到命令,并执行命令。

基本代码

客户端代码,创建一个具体命令对象并设定它的接收者

static void Main(string[] args)
        {
            Receiver r = new Receiver();
            Command c = new ConcreteCommand(r);
            Invoker i = new Invoker();

           
            i.SetCommand(c);
            i.ExecuteCommand();

            Console.Read();

        }

Command类,用来声明执行操作的接口

abstract class Command
    {
        protected Receiver receiver;
        public Command(Receiver receiver)
        {
            this.receiver = receiver;
        }
        abstract public void Execute();

    }

ConcreteCommand类,将一个接收者对象绑定于一个动作,调用接收者相应的操作,以实现Execute

class ConcreteCommand : Command
    {
        public ConcreteCommand(Receiver receiver)
            :
          base(receiver) { }

        public override void Execute()
        {
            receiver.Action();
        }
    }

Receiver类,知道如何实施与执行一个与请求相关的操作,任何类都可能作为一个接收者

class Receiver
    {
        public void Action()
        {
            Console.WriteLine("执行请求!");
        }
    }

Invoker类,要求该命令执行这个请求

class Invoker
    {
        private Command command;

        public void SetCommand(Command command)
        {
            this.command = command;
        }

        public void ExecuteCommand()
        {
            command.Execute();
        }
    }

例子

大鸟对小菜说肚子饿了,走,我请你吃烤串。

此时老板烤的第一批肉串好了。“老板,我要两串”、“老板,我要三串不辣的”、“老板。我刚才已经给钱了”。旁边的人七嘴八舌的叫开了,场面有点混乱,以致于老板已经产生错误的判断了,造成分发错误,收钱错误。

这时大鸟对小菜说,走吧我们还是换一家吧,于是大鸟和小菜走到了一家烤肉店。

服务员,我们要十串羊肉串、两串鸡翅、两瓶啤酒。

这时服务员说:“鸡翅没有了,要点别的吧”

“那就来四串板筋,微辣啊”

上面的例子是两种不同的经营方式,那么如果转换成程序是怎样的呢?

第一种的结构图(烧烤摊)


客户端代码

static void Main(string[] args)
        {
            Barbecuer boy = new Barbecuer();
            boy.BakeMutton();
            boy.BakeMutton();
            boy.BakeMutton();
            boy.BakeChickenWing();
            boy.BakeMutton();
            boy.BakeMutton();
            boy.BakeChickenWing();

            Console.Read();
        }

烤肉串者

public class Barbecuer
    {
        //烤羊肉串
        public void BakeMutton()
        {
            Console.WriteLine("烤羊肉串!");
        }
        //烤鸡翅
        public void BakeChickenWing()
        {
            Console.WriteLine("烤鸡翅!");
        }
    }

效果



第二种结构图(烧烤店)



客户端代码

static void Main(string[] args)
        {
            //开店前的准备
            Barbecuer boy = new Barbecuer();
            Command bakeMuttonCommand1 = new BakeMuttonCommand(boy);
            Command bakeMuttonCommand2 = new BakeMuttonCommand(boy);
            Command bakeChickenWingCommand1 = new BakeChickenWingCommand(boy);
            Waiter girl = new Waiter();

            //开门营业 顾客点菜
            girl.SetOrder(bakeMuttonCommand1);
            girl.SetOrder(bakeMuttonCommand2);
            girl.SetOrder(bakeChickenWingCommand1);

            //点菜完闭,通知厨房
            girl.Notify();

            Console.Read();

        }

服务员

public class Waiter
    {
        private IList<Command> orders = new List<Command>();

        //设置订单
        public void SetOrder(Command command)
        {
            if (command.ToString() == "命令模式.BakeChickenWingCommand")
            {
                Console.WriteLine("服务员:鸡翅没有了,请点别的烧烤。");
            }
            else
            {
                orders.Add(command);
                Console.WriteLine("增加订单:" + command.ToString() + "  时间:" + DateTime.Now.ToString());
            }
        }

        //取消订单
        public void CancelOrder(Command command)
        {
            orders.Remove(command);
            Console.WriteLine("取消订单:" + command.ToString() + "  时间:" + DateTime.Now.ToString());
        }

        //通知全部执行
        public void Notify()
        {
            foreach (Command cmd in orders)
            {
                cmd.ExcuteCommand();
            }
        }
    }

抽象命令

public abstract class Command
    {
        protected Barbecuer receiver;

        public Command(Barbecuer receiver)
        {
            this.receiver = receiver;
        }

        //执行命令
        abstract public void ExcuteCommand();
    }

烤羊肉串命令

class BakeMuttonCommand : Command
    {
        public BakeMuttonCommand(Barbecuer receiver)
            : base(receiver)
        { }

        public override void ExcuteCommand()
        {
            receiver.BakeMutton();
        }
    }

烤鸡翅命令

class BakeChickenWingCommand : Command
    {
        public BakeChickenWingCommand(Barbecuer receiver)
            : base(receiver)
        { }

        public override void ExcuteCommand()
        {
            receiver.BakeChickenWing();
        }
    }

烤肉串者

public class Barbecuer
    {
        public void BakeMutton()
        {
            Console.WriteLine("烤羊肉串!");
        }

        public void BakeChickenWing()
        {
            Console.WriteLine("烤鸡翅!");
        }
    }

效果图

命令模式的优点

1.类间解耦。调用者角色与接收者角色之间没有任何依赖关系,调用者实现功能时只需要调用Command抽象类的execute方法就可以,不需要了解到底是哪个接收者执行

2.可扩展性。Command的子类可以非常容易地扩展,而调用者Invoker和高层次的模块Client不产生严重的代码耦合

3.命令模式结合其他模式会更优秀。命令模式可以结合责任链模式,实现命令族解析任务;结合模板方法模式,则可以减少Command子类的膨胀问题。

命令模式的缺点

Command子类中如果有N个命令,问题就出来了,Comma的子类就不可以。


  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 18
    评论
命令模式是一种行为设计模式,它允许您将操作封装在对象中,并通过在对象之间传递这些对象来解耦发送者和接收者。以下是一个简单的命令模式案例: 假设我们有一个遥控器,它可以控制一个灯。我们可以使用命令模式来实现遥控器的行为。首先,我们定义一个命令接口,例如: ``` public interface Command { public void execute(); } ``` 然后,我们实现一个具体的命令类,例如打开灯的命令: ``` public class TurnOnLightCommand implements Command { private Light light; public TurnOnLightCommand(Light light) { this.light = light; } public void execute() { light.turnOn(); } } ``` 这里的 `Light` 是一个接收者对象,它有一个 `turnOn()` 方法用于打开灯。然后,我们可以定义一个遥控器类,它有两个按钮,一个用于打开灯,另一个用于关闭灯: ``` public class RemoteControl { private Command turnOnCommand; private Command turnOffCommand; public RemoteControl(Command turnOnCommand, Command turnOffCommand) { this.turnOnCommand = turnOnCommand; this.turnOffCommand = turnOffCommand; } public void pressTurnOnButton() { turnOnCommand.execute(); } public void pressTurnOffButton() { turnOffCommand.execute(); } } ``` 最后,我们可以使用以下代码来测试我们的命令模式实现: ``` Light light = new Light(); Command turnOnCommand = new TurnOnLightCommand(light); Command turnOffCommand = new TurnOffLightCommand(light); RemoteControl remoteControl = new RemoteControl(turnOnCommand, turnOffCommand); remoteControl.pressTurnOnButton(); // 打开灯 remoteControl.pressTurnOffButton(); // 关闭灯 ``` 这就是一个简单的命令模式案例,它允许我们将操作封装在对象中并解耦发送者和接收者。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 18
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值