大话设计模式C++达到-文章16章-国家模式
2015-10-05 18:54
549 查看
一、UML画画
二、概念
状态模式(State):当一个对象的内在状态改变时同意改变其行为。这个对象看起来像是改变了其类。
三、说明
以下是来自书本和网络的对状态模式的定义和分析:
(1)状态模式同意对象在内部状态改变时改变它的行为,对象看起来好像改动了它的类。看起来,状态模式好像是神通广大非常厉害似的——竟然可以“改动自身的类”!
(2)适用场景:
a)状态模式主要解决的是当控制一个对象状态转换的条件表达式过于复杂时的情况。
把状态的推断逻辑转移到表示不同状态的一系列类中,能够把复杂的判 断逻辑简单化。(简单来说,就是把各种if else 转变成了一个个的详细状态,原来if else 每种情况下的操作如今转换到了某个详细状态中)
b)当一个对象行为取决于它的状态,而且它必须在执行时刻依据状态改变它的行为时。就能够考虑使用状态模式了。
四、角色
(1)Context类:在该类内部维护一个ConcreteState子类的一个实例,这个实例定义当前的状态。
(2)State类:抽象状态类,定义一个 接口以封装与Context的一个特定状态相关的行为。
(3)ConcreteStateA,ConcreteStateB类:详细状态类。每个子 类实现一个与Context的一个状态相关的行为。
五、C++实现
(1)State.h(抽象状态类和详细状态类的声明和定义都在State.h和State.cpp中)
(2)State.cpp
(3)Work.h(这里的Work就是状态模式中的Context)
(4)Work.cpp
(5)main.cpp(client)
注意:上面的代码会出现两个类相互调用的情况。请查看日志:C++中两个类互相引用的解决方法
(6)执行截图
二、概念
状态模式(State):当一个对象的内在状态改变时同意改变其行为。这个对象看起来像是改变了其类。
三、说明
以下是来自书本和网络的对状态模式的定义和分析:
(1)状态模式同意对象在内部状态改变时改变它的行为,对象看起来好像改动了它的类。看起来,状态模式好像是神通广大非常厉害似的——竟然可以“改动自身的类”!
(2)适用场景:
a)状态模式主要解决的是当控制一个对象状态转换的条件表达式过于复杂时的情况。
把状态的推断逻辑转移到表示不同状态的一系列类中,能够把复杂的判 断逻辑简单化。(简单来说,就是把各种if else 转变成了一个个的详细状态,原来if else 每种情况下的操作如今转换到了某个详细状态中)
b)当一个对象行为取决于它的状态,而且它必须在执行时刻依据状态改变它的行为时。就能够考虑使用状态模式了。
四、角色
(1)Context类:在该类内部维护一个ConcreteState子类的一个实例,这个实例定义当前的状态。
(2)State类:抽象状态类,定义一个 接口以封装与Context的一个特定状态相关的行为。
(3)ConcreteStateA,ConcreteStateB类:详细状态类。每个子 类实现一个与Context的一个状态相关的行为。
五、C++实现
(1)State.h(抽象状态类和详细状态类的声明和定义都在State.h和State.cpp中)
#ifndef STATE #define STATE //#include "Work.h" extern class Work; class State { public: State(){}; virtual void writeProgram(Work* w){}; }; class ForenoonState:public State { public: void writeProgram(Work* w); }; class NoonState:public State { public: void writeProgram(Work* w); }; class AfternoonState:public State { public: void writeProgram(Work* w); }; class EveningState:public State { public: void writeProgram(Work* w); }; class SleepingState:public State { public: void writeProgram(Work* w); }; class RestState:public State { public: void writeProgram(Work* w); }; #endif
(2)State.cpp
#include <iostream> #include "State.h" #include "Work.h" using namespace std; void ForenoonState::writeProgram(Work* w) { if(w->getHour()<12) { cout<<"当前时间:"<<w->getHour()<<"点 "<<"上午工作,精神百倍"<<endl; } else { w->setState(new NoonState); w->writeProgram(); } } void NoonState::writeProgram(Work* w) { if(w->getHour()<13) { cout<<"当前时间:"<<w->getHour()<<"点 "<<"饿了,午饭。犯困。午休"<<endl; } else { w->setState(new AfternoonState); w->writeProgram(); } } void AfternoonState::writeProgram(Work* w) { if(w->getHour()<17) cout<<"当前时间:"<<w->getHour()<<"点 "<<"下午状态还不错,继续努力"<<endl; else { w->setState(new EveningState); w->writeProgram(); } } void EveningState::writeProgram(Work* w) { if(w->getFinish()) { w->setState(new RestState); w->writeProgram(); } else { if(w->getHour()<21) cout<<"当前时间:"<<w->getHour()<<"点 "<<"加班哦,疲惫至极"<<endl; else { w->setState(new SleepingState); w->writeProgram(); } } } void SleepingState::writeProgram(Work* w) { cout<<"当前时间:"<<w->getHour()<<"点 "<<"不行了,睡着了"<<endl; } void RestState::writeProgram(Work* w) { cout<<"当前时间:"<<w->getHour()<<"点 "<<"下班回家了"<<endl; }
(3)Work.h(这里的Work就是状态模式中的Context)
#ifndef WORK #define WORK #include "State.h" class Work { private: State* current; double Hour; bool finish; public: Work(); ~Work(); double getHour(); void setHour(double HOUR); bool getFinish(); void setFinish(bool FINISH); void setState(State* s); void writeProgram(); }; #endif
(4)Work.cpp
#include "Work.h" Work::Work() { current=new ForenoonState; Hour=9; finish=false; } Work::~Work() { if(current!=0) delete current; } double Work::getHour() { return Hour; } void Work::setHour(double HOUR) { Hour=HOUR; } bool Work::getFinish() { return finish; } void Work::setFinish(bool FINISH) { finish=FINISH; } void Work::setState(State* s) { if(current!=0) delete current; current=s; } void Work::writeProgram() { current->writeProgram(this); }
(5)main.cpp(client)
#include <iostream> #include <cstdlib> #include "Work.h" //#include "State.h" using namespace std; void main() { Work emergencyProjects; emergencyProjects.setHour(9); emergencyProjects.writeProgram(); emergencyProjects.setHour(10); emergencyProjects.writeProgram(); emergencyProjects.setHour(12); emergencyProjects.writeProgram(); emergencyProjects.setHour(13); emergencyProjects.writeProgram(); emergencyProjects.setHour(14); emergencyProjects.writeProgram(); emergencyProjects.setHour(17); emergencyProjects.writeProgram(); emergencyProjects.setFinish(false); emergencyProjects.setHour(19); emergencyProjects.writeProgram(); emergencyProjects.setHour(22); emergencyProjects.writeProgram(); system("pause"); }
注意:上面的代码会出现两个类相互调用的情况。请查看日志:C++中两个类互相引用的解决方法
(6)执行截图
相关文章推荐
- C++中int型128转入char型变量c中
- 深入理解C/C++ [Deep C (and C++)]
- C语言中指针数组和数组指针
- 【C++学习】float与double的范围和精度
- Bridge(桥接)设计模式
- C++11新特性--右值引用
- 【源码】员工管理系统c++大型实验,含实验报告
- C/C++基本输入输出函数
- 面试复习(C++)之希尔排序
- 第二周-项目1 - C/C++语言中函数参数传递的三种方式
- C++中赋值运算符与逗号运算符的用法详解
- C++中对象的赋值与复制操作详细解析
- C++中复制构造函数和重载赋值操作符总结
- 设计模式C++达到 3.抽象工厂
- 【第4周 项目6 - 多项式求和】
- 深入C++中构造函数、拷贝构造函数、赋值操作符、析构函数的调用过程总结
- 【第4周 项目5 - 猴子选大王】
- 第六周-项目2 - 建立链栈算法库
- 【第4周 项目3 - 单链表应用(2)】
- C++继承方式