模式特点
将请求封装为对象,从而允许用不同的请求对客户端进行参数化、排队或记录请求日志,以及支持撤销操作。
- 将请求的调用者与接收者解耦
- 命令对象可以排队、延迟执行、记录日志
- 支持撤销和重做(Undo/Redo)
- 宏命令:组合多个命令一次性执行
类图
应用场景
- Qt 中的 QUndoCommand 和 QUndoStack 撤销框架
- 示教器图形化编程:每条运动指令封装为命令对象
- UI 菜单和按钮操作:点击触发对应命令
- 任务队列:将命令排队,由工作线程逐个执行
- 远程调用:将请求封装为命令对象进行序列化传输
示例代码(C++)
// 接收者 - 机器人运动控制 class RobotArm { public: void moveTo(double x, double y) { std::cout << "移动到(" << x << "," << y << ")" << std::endl; } void moveBack(double x, double y) { std::cout << "从(" << x << "," << y << ")返回" << std::endl; } }; // 抽象命令 class Command { public: virtual void execute() = 0; virtual void undo() = 0; virtual ~Command() = default; }; // 具体命令 class MoveCommand : public Command { RobotArm* m_robot; double m_x, m_y; public: MoveCommand(RobotArm* r, double x, double y) : m_robot(r), m_x(x), m_y(y) {} void execute() override { m_robot->moveTo(m_x, m_y); } void undo() override { m_robot->moveBack(m_x, m_y); } }; // 调用者 - 命令历史管理 class CommandManager { std::vector<Command*> m_history; public: void executeCommand(Command* cmd) { cmd->execute(); m_history.push_back(cmd); } void undoLast() { if (!m_history.empty()) { m_history.back()->undo(); m_history.pop_back(); } } }; RobotArm robot; CommandManager manager; manager.executeCommand(new MoveCommand(&robot, 100, 200)); manager.undoLast(); // 撤销上次移动