此为大话设计模式中的状态模式的c++版本
因为此代码中各个类的相互依赖比较严重,所以加入了头文件将声明放置在头文件之中
state.h
/*
* state.h
*
* Created on: Aug 10, 2017
* Author: clh01s@163.com
*/
#ifndef _STATE_H_
#define _STATE_H_
#include <iostream>
#include <string>
class State;
//维护一个concreteState的实例,这个实例定义当前状态
class Work
{
public:
//因为相互包含的问题实现在移至下方
Work();
void Set_state(State *s);
//时间的设置和获取函数
void Set_hour(double hour);
double Get_hour();
void Write_program();
void Set_task_finished(bool finish);
bool Get_task_finished();
private:
State *_current;
double _hour = 0;
//任务状态
bool _finish = false;
};
class State
{
public:
virtual ~State(){}
//定义一个工作接口交给子类实现
virtual void Write_program(Work *w){};
};
class ForenoonState:public State
{
public:
void Write_program(Work *w) override;
};
class NoonState:public State
{
public:
//实现基类的工作函数
void Write_program(Work *w) override;
};
//下午工作类
class AfternoonState:public State
{
public:
//实现基类的工作函数
void Write_program(Work *w) override;
};
//傍晚工作类
class EveningState:public State
{
public:
//实现基类的工作函数
void Write_program(Work *w) override;
};
//睡眠类
class SleepingState:public State
{
public:
//实现基类的工作函数
void Write_program(Work *w) override;
};
//下班类
class RestState:public State
{
public:
//实现基类的工作函数
void Write_program(Work *w) override;
};
#endif /* _STATE_H_ */
state.cpp
/*
* state.cpp
*
* Created on: Aug 7, 2017
* Author: clh01s@163.com
* 状态模式
* 允许一个对象在其内部状态改变时
* 改变它的行为.对象看起来似乎修
* 改了他的类.
*/
#include "state.h"
using namespace std;
void ForenoonState::Write_program(Work *w)
{
//检查时间是否小于12点
if(w->Get_hour() < 12)
{
cout<<"上午工作时间,精神饱满!!时间:"<<w->Get_hour()<<endl;
}else
{
//将指针设置为中午工作
w->Set_state(new NoonState());
//继续调用WriteProgram函数检查时间
w->Write_program();
}
}
void NoonState::Write_program(Work *w)
{
//检查时间是否小于13点
if(w->Get_hour() < 13)
{
cout<<"中午工作时间,饿了,吃饭!!时间:"<<w->Get_hour()<<endl;
}else
{
//将指针设置为下午工作
w->Set_state(new AfternoonState());
//继续调用WriteProgram函数检查时间
w->Write_program();
}
}
void AfternoonState::Write_program(Work *w)
{
//检查时间是否小于17点
if(w->Get_hour() < 17)
{
cout<<"下午工作时间,精神还行!!时间:"<<w->Get_hour()<<endl;
}else
{
//将指针设置为傍晚工作
w->Set_state(new EveningState());
//继续调用WriteProgram函数检查时间
w->Write_program();
}
}
void EveningState::Write_program(Work *w)
{
//检查任务是否完成
if(w->Get_task_finished())
{
//如果是下班就转入下班状态
w->Set_state(new RestState());
w->Write_program();
}else
{
//检查时间是否小于21点
if(w->Get_hour() < 21)
{
cout<<"加班中......时间:"<<w->Get_hour()<<endl;
}else
{
//将指针设置为傍晚工作
w->Set_state(new SleepingState());
//继续调用WriteProgram函数检查时间
w->Write_program();
}
}
}
void SleepingState::Write_program(Work *w)
{
//因为到深夜所以直接输出吃不消
cout<<"吃不消了,睡着了,时间:"<<w->Get_hour()<<endl;
}
void RestState::Write_program(Work *w)
{
//完成工作的输出
cout<<"下班回家,时间:"<<w->Get_hour();
}
//work类的构造函数实现
Work::Work()
{
//将上午工作的类的指针赋值给_current指针变量
_current = new ForenoonState();
}
//用于修改_current指针变量
void Work::Set_state(State *s)
{
_current = s;
}
//时间的设置和获取函数
void Work::Set_hour(double hour)
{
_hour = hour;
}
double Work::Get_hour()
{
return _hour;
}
void Work::Write_program()
{
//用已经在构造函数被赋上ForenoonState类的地址的_current
//调用ForenoonState类的Write_program函数
//并且传入Work类的地址让其可以继续调用Work类中的其它函数
_current->Write_program(this);
}
void Work::Set_task_finished(bool finish)
{
_finish = finish;
}
bool Work::Get_task_finished()
{
return _finish;
}
int main()
{
//紧急项目
Work *emergencyProjects = new Work();
//上班时间
emergencyProjects->Set_hour(9);
emergencyProjects->Write_program();
emergencyProjects->Set_hour(10);
emergencyProjects->Write_program();
emergencyProjects->Set_hour(11);
emergencyProjects->Write_program();
emergencyProjects->Set_hour(12);
emergencyProjects->Write_program();
emergencyProjects->Set_hour(13);
emergencyProjects->Write_program();
emergencyProjects->Set_hour(14);
emergencyProjects->Write_program();
emergencyProjects->Set_hour(17);
//任务没有完成
emergencyProjects->Set_task_finished(false);
emergencyProjects->Write_program();
emergencyProjects->Set_hour(19);
emergencyProjects->Write_program();
emergencyProjects->Set_hour(22);
emergencyProjects->Write_program();
//释放资源
delete emergencyProjects;
return 0;
}
State模式的适用性(摘录自《设计模式》):
1.一个对象的行为取决于他的状态,并且它必须在运行时刻根据状态改变他的行为.
2.一个操作中含有庞大的多分支的条件语句,且这些分支依赖与该对象的状态.这个状态常用一个或多个枚举常量表示.State模式将每个条件分支放入一个独立的类中.这使得你可以根据对象自身的情况将对象的状态作为一个对象,这以对象可以不依赖与其他对象而独立变化.
State模式的优点(摘录自《设计模式》):
1.它将与特定状态相关的行为局部化,并且将不同状态的行为分割开来 State模式将所有与一个特定的状态热爱相关的行为都放入一个对象中.因为所有与状态相关的代码都存在于某个State子类中,所以通过定义新的子类可以很容易的增加新的状态和转换.
2.它使得状态转换显式化 当一个对象仅以内部数据值来定义当前状态时,其状态仅表现为对一些变量的复制,这不够明确.为不同的状态引入独立的对象使得转换变得更加的明确.而且State对象可以保证context不会发生内部状态不一致的情况,因为从context角度看状态转换是原子的——–只需重新绑定一个变量(即context的State对象变量)而无需为多个变量赋值
3.State对象可以被共享 如果State对象没有实例变量——-即它们表示的状态完全以它们的类型来编码——那么各context对象可以共享一个State对象.当状态以这种方式被共享时,它们必然是没有内部状态,只有行为的轻量级对象.
转载请注明源地址:http://blog.csdn.net/clh01s