2021年9月27日-设计模式之命令模式

第十五章:命令模式

一、基本介绍

1)命令模式有三个组成部分:命令发起者(Invoker)、命令(Command)、命令接收者(Receiver)

2)消除了命令发起者和接收者之间的耦合

3)命令模式还支持撤销的操作

基本类图:

在这里插入图片描述

二、模式实例

实现指挥官可以向士兵发送命令,指挥行动的功能

在这里插入图片描述

Command 抽象类

public abstract class Command {
    abstract public void execute();
    abstract public void undo();
}

命令接收者类

Archer

public class Archer {
    public void fireAtWill() {
        System.out.println("弓箭手:正在自由射击");
    }

    public void stopFire() {
        System.out.println("弓箭手:停止射击中");
    }
}

Cavalry

public class Cavalry {
    public void charge() {
        System.out.println("骑兵:To Death!!!");
    }

    public void fallback() {
        System.out.println("骑兵:正在远离战场");
    }
}

具体命令类

ArcherFireCommand

public class ArcherFireCommand extends Command {
    private Archer archer;

    public ArcherFireCommand(Archer archer) {
        this.archer = archer;
    }

    public void setArcher(Archer archer) {
        this.archer = archer;
    }

    @Override
    public void execute() {
        System.out.println("指挥官:自由射击");
        archer.fireAtWill();
    }

    @Override
    public void undo() {
        System.out.println("指挥官:撤销命令");
        archer.stopFire();
    }
}

ArcherStopCommand

public class ArcherStopCommand extends Command {
    private Archer archer;

    public ArcherStopCommand(Archer archer) {
        this.archer = archer;
    }

    public void setArcher(Archer archer) {
        this.archer = archer;
    }

    @Override
    public void execute() {
        System.out.println("指挥官:停止射击");
        archer.stopFire();
    }

    @Override
    public void undo() {
        System.out.println("指挥官:撤销命令");
        archer.fireAtWill();
    }
}

CavalryBackCommand

public class CavalryBackCommand extends Command {
    private Cavalry cavalry;

    public CavalryBackCommand(Cavalry cavalry) {
        this.cavalry = cavalry;
    }

    public void setCavalry(Cavalry cavalry) {
        this.cavalry = cavalry;
    }

    @Override
    public void execute() {
        System.out.println("指挥官:骑兵撤离战场");
        cavalry.fallback();
    }

    @Override
    public void undo() {
        System.out.println("指挥官:撤销命令");
        cavalry.charge();
    }
}

CavalryChargeCommand

public class CavalryChargeCommand extends Command{
    private Cavalry cavalry;

    public CavalryChargeCommand(Cavalry cavalry) {
        this.cavalry = cavalry;
    }

    public void setCavalry(Cavalry cavalry) {
        this.cavalry = cavalry;
    }

    @Override
    public void execute() {
        System.out.println("指挥官:骑兵冲锋!");
        cavalry.charge();
    }

    @Override
    public void undo() {
        System.out.println("指挥官:撤销命令");
        cavalry.fallback();
    }
}

空命令类

public class BlankCommand extends Command {
    @Override
    public void execute() {

    }

    @Override
    public void undo() {

    }
}

命名发出者类

public class Commander {
    private Map<String, Command> commands;
    private Command preCommand;
    private Command blankCommand;

    public Commander() {
        this.commands = new HashMap<>(8);
        this.blankCommand = new BlankCommand();
    }

    public void addCommand(String id, Command command) {
        commands.put(id, command);
    }

    public void releaseCommand(String id) {
        Command command = commands.get(id);
        if (command == null) {
            command = this.blankCommand;
        }
        command.execute();
        this.preCommand = command;
    }

    public void recallCommand() {
        this.preCommand.undo();
    }
}

测试类

public class CommandTest {
    public static void main(String[] args) {
        Commander commander = new Commander();

        Archer archer = new Archer();
        ArcherFireCommand archerFireCommand = new ArcherFireCommand(archer);
        ArcherStopCommand archerStopCommand = new ArcherStopCommand(archer);
        commander.addCommand("F2F3", archerFireCommand);
        commander.addCommand("F2F1", archerStopCommand);

        Cavalry cavalry = new Cavalry();
        CavalryChargeCommand cavalryChargeCommand = new CavalryChargeCommand(cavalry);
        CavalryBackCommand cavalryBackCommand = new CavalryBackCommand(cavalry);
        commander.addCommand("F1F3", cavalryChargeCommand);
        commander.addCommand("F1F5", cavalryBackCommand);

        commander.releaseCommand("F2F3");
        commander.recallCommand();
        commander.releaseCommand("F1F3");
        commander.recallCommand();
    }
}


/********** result **********
指挥官:自由射击
弓箭手:正在自由射击
指挥官:撤销命令
弓箭手:停止射击中
指挥官:骑兵冲锋!
骑兵:To Death!!!
指挥官:撤销命令
骑兵:正在远离战场
*********** result **********/

三、优缺点

优点:

  • 命令对象将 Invoker 和 Receiver 解耦
  • 容易设计一个命令队列,只要将命令放入队列就可以多线程执行命令
  • 容易实现对命令的撤销和重做

缺点:

  • 导致过多具体的命令类

命令发出者的命令容器里可以预存空命令,这样就没必要每次判空

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值