前情回顾:Day 7 重点回顾
在 Day 7 中,我们彻底讲透了观察者模式:
它是典型的行为型模式,核心理念是“一变多知”,当一个对象状态变化时,自动通知所有订阅者。
我们通过 RxCpp 实现了工业级的事件广播系统,实现了多个模块订阅同一个数据源。
实战中,如协议解包系统、GUI 事件响应、股票系统等,都广泛采用观察者机制。
观察者模式强调“自动推送消息”,而今天我们进入策略模式,它更强调“主动选择行为”!
策略模式(Strategy Pattern)是行为型设计模式中最具“切换能力”的一个,它的设计哲学非常明确:
将算法(行为)抽象为可替换的策略,使得行为的改变不依赖于使用它的对象本身。
策略模式特别适合处理:
本篇 Day 8,将从“动机、结构、语法、实战场景、项目代码、面试回答”六大维度,构建你对策略模式的完整掌握。
如果使用 if-else
分支写法:
if (type == "alipay") {
...
} else if (type == "wechat") {
...
}
✅ 缺点:
这时就需要策略模式!
+------------------+
| Strategy |<------------------------------+
+------------------+ |
| + execute() | |
+------------------+ |
/\ |
|| |
+-------------------+ +-----------------------+ |
| AlipayStrategy | | WeChatStrategy | |
+-------------------+ +-----------------------+ |
| + execute() | | + execute() | |
+-------------------+ +-----------------------+ |
|
+------------------------------+ |
| PaymentContext |-----+
+------------------------------+
| - strategy: Strategy* |
| + setStrategy(Strategy*) |
| + pay() |
+------------------------------+
角色 | 职责 |
---|---|
Strategy | 策略接口,声明统一算法方法 |
ConcreteStrategy | 具体策略类,封装各自逻辑 |
Context | 上下文,持有当前策略对象 |
class PaymentStrategy {
public:
virtual void pay(int amount) = 0;
virtual ~PaymentStrategy() = default;
};
class AlipayStrategy : public PaymentStrategy {
public:
void pay(int amount) override {
std::cout << "使用支付宝支付: " << amount << " 元" << std::endl;
}
};
class WeChatStrategy : public PaymentStrategy {
public:
void pay(int amount) override {
std::cout << "使用微信支付: " << amount << " 元" << std::endl;
}
};
class CreditCardStrategy : public PaymentStrategy {
public:
void pay(int amount) override {
std::cout << "使用信用卡支付: " << amount << " 元" << std::endl;
}
};
class PaymentContext {
private:
std::unique_ptr<PaymentStrategy> strategy_;
public:
void setStrategy(std::unique_ptr<PaymentStrategy> strategy) {
strategy_ = std::move(strategy);
}
void pay(int amount) {
if (strategy_)
strategy_->pay(amount);
else
std::cout << "未设置支付方式!" << std::endl;
}
};
int main() {
PaymentContext context;
context.setStrategy(std::make_unique<AlipayStrategy>());
context.pay(100);
context.setStrategy(std::make_unique<WeChatStrategy>());
context.pay(200);
context.setStrategy(std::make_unique<CreditCardStrategy>());
context.pay(300);
return 0;
}
应用领域 | 策略角色示例 |
---|---|
支付系统 | 支付方式切换:微信、支付宝、银行卡 |
压缩服务 | gzip、zip、lz4 等算法策略 |
游戏角色AI | 攻击策略、防御策略、逃跑策略 |
电商促销系统 | 折扣策略、满减策略、积分兑换策略 |
导航/路径规划 | 最快路线、最短路线、避开拥堵路线 |
编解码框架 | JSON、XML、YAML 策略 |
图像处理 | 多种滤镜、降噪算法策略 |
对比项 | 策略模式 | 状态模式 | 工厂模式 |
---|---|---|---|
意图 | 封装行为算法,动态切换 | 封装对象状态与行为 | 封装创建过程,替代 new |
变化点 | 行为逻辑 | 状态 + 行为 | 对象类型 |
是否持有引用 | Context 中持有策略对象 | 状态机中持有当前状态对象 | 工厂方法中返回具体对象 |
✅ 回答示例:
“在我们支付平台中使用了策略模式来解耦支付方式。我们定义了
PaymentStrategy
接口,具体实现了AlipayStrategy
、WeChatStrategy
等类,业务调用通过PaymentContext
设置策略并执行。策略模式让新增支付方式变得非常方便,无需改动旧逻辑,只需新增类即可。”
✅ 加分点:
std::unique_ptr
管理生命周期“行为封装进策略,替换逻辑不靠 if,扩展功能加新类,变化收敛更灵活。”
命令模式(Command Pattern)实战详解:解耦请求者与执行者,构建可撤销、可重做、可排队的操作系统。