状态模式
定义:
允许一个对象在内部状态改变时改变其行为
优点:
(1)封装了状态的转换规则,可以对状态对象统一管理而不是分散到一个业务代码中
(2)注入不同的状态对象实现不同的行为
(3)环境对象可以共享状态对象
缺点:
(1)结构和实现都很复杂容易导致代码混乱,且多半存在环境类与状态类相互依赖情况
(2)增加状态类须同时修改状态转换源代码,不满足开闭原则
使用范围:
对象的行为依赖于不同的对象状态,且对象状态间具有独立性
如:银行账户有正常、销户、欠费等
结构:
context:上下文类,负责状态转换操作
state_pattern:状态抽象类
solid_state_pattern,liquid_state_pattern,gas_state_pattern:具体状态类
实现:
namespace behavioral_pattern
{
class state_pattern
{
public:
virtual void solid() { std::cout << "固体不支持" << std::endl; }
virtual void liquid() { std::cout << "液体不支持" << std::endl; }
virtual void gas() { std::cout << "气体不支持" << std::endl; }
};
class solid_state_pattern : public state_pattern
{
public:
void solid()
{
std::cout << "固体-- 雕刻" << std::endl;
}
};
class liquid_state_pattern : public state_pattern
{
public:
void liquid()
{
std::cout << "液体-- 饮用" << std::endl;
}
};
class gas_state_pattern : public state_pattern
{
public:
void gas()
{
std::cout << "气体-- 降温" << std::endl;
}
};
class context
{
public:
void set_status(std::shared_ptr<state_pattern> s) { this->status = s; }
void change(int temp)
{
if (0 > temp)
status->solid();
else if (100 < temp)
status->gas();
else
status->liquid();
}
private:
std::shared_ptr<state_pattern> status;
};
}
测试:
基于GoogleTest 的单元测试框架;框架可参考如下网址:
https://www.cnblogs.com/jycboy/p/gtest_catalog.html
using namespace behavioral_pattern;
TEST(test_state_pattern_context_change, success_set_status)
{
context cont;
std::shared_ptr<state_pattern> share_state{new solid_state_pattern()};
cont.set_status(share_state);
cont.change(-1);
}
总结
(1)状态模式考虑是否是多个环境类共享状态情况(需要定义静态状态对象在转换类中)
(2)考虑状态间是否会自动转换而不是通过客户端实现转换,自动转换需要相互依赖
(3)抽象状态类需定义状态类的所有方法,具体状态类重新特定方法