当前位置: 首页 > news >正文

C++命令模式与请求封装

C++命令模式与请求封装

命令模式将请求封装为对象,支持参数化、队列化和可撤销操作。这是实现撤销/重做、事务和任务调度的基础。

命令接口定义execute方法。

#include
#include
#include
#include
#include

class Command {
public:
virtual ~Command() = default;
virtual void execute() = 0;
virtual void undo() = 0;
virtual std::string name() const = 0;
};

class Light {
public:
void on() { std::cout << "Light ON\n"; }
void off() { std::cout << "Light OFF\n"; }
};

class LightOnCommand : public Command {
Light& light_;
public:
explicit LightOnCommand(Light& l) : light_(l) {}
void execute() override { light_.on(); }
void undo() override { light_.off(); }
std::string name() const override { return "Light On"; }
};

class LightOffCommand : public Command {
Light& light_;
public:
explicit LightOffCommand(Light& l) : light_(l) {}
void execute() override { light_.off(); }
void undo() override { light_.on(); }
std::string name() const override { return "Light Off"; }
};

class Fan {
int speed_ = 0;
public:
void high() { speed_ = 3; std::cout << "Fan HIGH\n"; }
void medium() { speed_ = 2; std::cout << "Fan MEDIUM\n"; }
void low() { speed_ = 1; std::cout << "Fan LOW\n"; }
void off() { speed_ = 0; std::cout << "Fan OFF\n"; }
int speed() const { return speed_; }
};

class FanCommand : public Command {
Fan& fan_;
int prev_speed_;
int new_speed_;
std::string name_;
public:
FanCommand(Fan& f, int speed, const std::string& n)
: fan_(f), new_speed_(speed), name_(n) {}

void execute() override {
prev_speed_ = fan_.speed();
switch (new_speed_) {
case 3: fan_.high(); break;
case 2: fan_.medium(); break;
case 1: fan_.low(); break;
default: fan_.off(); break;
}
}

void undo() override {
switch (prev_speed_) {
case 3: fan_.high(); break;
case 2: fan_.medium(); break;
case 1: fan_.low(); break;
default: fan_.off(); break;
}
}

std::string name() const override { return name_; }
};

class RemoteControl {
std::vector> on_commands_;
std::vector> off_commands_;
std::stack history_;

public:
void set_command(int slot, std::unique_ptr on, std::unique_ptr off) {
if (slot >= on_commands_.size()) {
on_commands_.resize(slot + 1);
off_commands_.resize(slot + 1);
}
on_commands_[slot] = std::move(on);
off_commands_[slot] = std::move(off);
}

void on_button(int slot) {
if (slot < on_commands_.size() && on_commands_[slot]) {
on_commands_[slot]->execute();
history_.push(on_commands_[slot].get());
}
}

void off_button(int slot) {
if (slot < off_commands_.size() && off_commands_[slot]) {
off_commands_[slot]->execute();
history_.push(off_commands_[slot].get());
}
}

void undo() {
if (!history_.empty()) {
history_.top()->undo();
history_.pop();
}
}
};

void command_demo() {
Light light;
Fan fan;

RemoteControl remote;
remote.set_command(0,
std::make_unique(light),
std::make_unique(light));
remote.set_command(1,
std::make_unique(fan, 3, "Fan High"),
std::make_unique(fan, 0, "Fan Off"));

remote.on_button(0);
remote.on_button(1);
remote.off_button(0);
remote.undo();
remote.undo();
remote.undo();
}

宏命令组合多个命令。

class MacroCommand : public Command {
std::vector commands_;
public:
void add(Command* cmd) { commands_.push_back(cmd); }

void execute() override {
for (auto* cmd : commands_) cmd->execute();
}

void undo() override {
for (auto it = commands_.rbegin(); it != commands_.rend(); ++it) {
(*it)->undo();
}
}

std::string name() const override { return "Macro"; }
};

函数式命令使用lambda。

class FunctionalCommand : public Command {
std::function execute_;
std::function undo_;
std::string name_;
public:
FunctionalCommand(std::function exec, std::function und,
std::string n)
: execute_(std::move(exec)), undo_(std::move(und)), name_(std::move(n)) {}

void execute() override { execute_(); }
void undo() override { undo_(); }
std::string name() const override { return name_; }
};

void functional_command_demo() {
int value = 0;
int previous = 0;

auto inc = std::make_unique(
[&]() { previous = value; value += 10; std::cout << "Value: " << value << "\n"; },
[&]() { value = previous; std::cout << "Undo: " << value << "\n"; },
"Increment"
);

inc->execute();
inc->execute();
inc->undo();
}

命令模式将调用者与接收者解耦,支持操作排队和撤销。

http://www.gsyq.cn/news/1538815.html

相关文章:

  • NGA论坛工作流优化工具:构建高效信息处理系统
  • 2026年上海铝合金门窗品牌选购指南:技术实力与服务体系深度评测 - 优质品牌商家
  • 嵌入式USB开发实战:从Freescale协议栈配置到调试优化全解析
  • 2026年工装装修公司推荐排行榜:办公楼/厂房/店铺/酒店/商场装修,专业设计与品质施工实力品牌精选 - 品牌发掘
  • 2026年青绿苔草优质生产企业官方甄选指南:从苗圃品质到景观工程的全维度分析 - 优质品牌商家
  • 2026年南宁装修墙板市场盘点:五家专业服务商深度解析与选择建议 - 品牌鉴赏官2026
  • 自动驾驶工程师:横跨感知、规控、安全的硬核工程角色
  • 2026乐山鳝丝品牌甄选本地人反复光顾的临江鳝丝门店指南 - 优质品牌商家
  • 2026年硼砂品牌官方甄选指南:从供应链到技术服务综合考量 - 优质品牌商家
  • 如何让重要网页永不消失?网页时光机浏览器扩展揭秘
  • 2026年 东三省体育培训/沈阳体育四项集训/辽宁体育升学指导榜单:体育统招升学与全日制补习机构深度推荐 - 品牌发掘
  • Grbl_Esp32架构革新:ESP32平台上的高精度CNC控制算法与模块化设计突破
  • 痛苦只在我痛的时候说话——沉默的伦理模块
  • 2026年深圳知识产权诉讼律师推荐:5位双资质实战专家 - 本地品牌推荐
  • 5个关键步骤:掌握VirtualApp安卓沙盒技术,实现应用多开与安全隔离
  • 2026成都艺考文化补习机构实测评测:聚焦核心维度 - 优质品牌商家
  • 如何为旧款Mac注入新生命:终极兼容性解决方案完整指南
  • 2026年紫外荧光硫测定仪厂商实力甄选:技术传承与行业应用深度解析 - 优质品牌商家
  • 2026年常州地板厂家推荐榜:SPC石塑地板/WPC木塑地板/强化复合地板/黑金刚地板/三层实木地板源头实力厂商精选 - 品牌发掘
  • 2026年成都防护网厂家权威排行:成都踏步钢格板/成都钢格栅板/成都防滑钢格板/成都鹿网/10家合规企业实测盘点 - 优质品牌商家
  • 2026年四川中青旅与同行服务能力实测评测:四川中青旅联系/稻城亚丁四姑娘山旅游/美国旅游/排行一览 - 优质品牌商家
  • 2026年青海草制品市场口碑观察:五家本土服务商综合评测 - 优质品牌商家
  • 基于Yocto Project为NXP LS1046A构建与部署嵌入式Linux系统实战指南
  • 唐山房屋渗漏水检测维修、卫生间漏水免砸砖维修、漏水点精准检测、厨房漏水防水补漏、正规防水补漏公司、口碑榜TOP5靠谱推荐、本地人必选的防水维修公司 - 安佳防水
  • 大连房屋渗漏水检测维修、卫生间漏水免砸砖维修、漏水点精准检测、厨房漏水防水补漏、正规防水补漏公司、口碑榜TOP5靠谱推荐、本地人必选的防水维修公司 - 安佳防水
  • 2026年行业甄选:口碑与性能兼优的真空出料泵厂家官方推荐指南 - 优质品牌商家
  • PIC16F54软件模拟Microwire驱动93LC66B EEPROM实战详解
  • 汽车电子PMIC设计实战:以NXP PF8100为例解析电源管理核心
  • 宜宾护墙板定制技术解析:侘寂风全屋定制/北欧风全屋定制/宜宾enf级环保板材定制/从选材到落地的全链路标准 - 优质品牌商家
  • 15款降AIGC网站实测:千笔AI遥遥领先