状态模式

当一个对象的内在状态改变时允许改变其行为,这个对象看起来像是改变了其类。

状态模式主要解决的是当控制一个对象状态转换的条件表达式过于复杂时的情况。把状态的判断逻辑转移到表示不同状态的一系列类当中,可以把复杂的判断逻辑简化。

将与特点状态相关的行为局部化,并且将不同状态的行为分割开来!

UML:

  

代码实现:

  以前很喜欢玩war3里面的国家对抗,是一个建造类游戏。里面的建筑在不同的时候有不同的状态,例如兵营在产兵的时候会发白光,

受伤的时候会着火,建造的时候有建筑特效。兵营在建造没完成的时候不能升级和产兵,升级的时候不能产兵,受伤着火了也能继续产兵或升级。

假设这些建筑的状态和表现为:建造-建造特效、受伤-受伤着火、升级-升级蓝光、生成-生产白光、修复-修复绿光。

实现各种状态代码state.h:

 #ifndef STATE_H
#define STATE_H
#include <iostream>
using namespace std; class absState{
public:
virtual void show() = ;
}; class buildingState:public absState{
public:
virtual void show()
{
cout<<"建造特效 ";
}
}; class fireState:public absState{
public:
virtual void show()
{
cout<<"受伤着火 ";
}
}; class productionState:public absState{
public:
virtual void show()
{
cout<<"生产白光 ";
}
}; class upGradeState:public absState
{
public:
virtual void show()
{
cout<<"升级蓝光 ";
}
}; class repairState:public absState
{
public:
virtual void show()
{
cout<<"修复绿光 ";
}
};
#endif

建筑实现代码building.h:

 #ifndef BUILDING_H
#define BUILDING_H
#include "state.h" #include <map>
#include <iostream>
using namespace std; enum StateType
{
BUILDING, INJURED, REPAIR, UPGRADE, PRODUCTION
}; class absBuilding
{
public:
absBuilding(char* name):mName(name){}
virtual void show()
{
cout<<mName<<"表现:"<<endl;
map<StateType, absState*>::iterator beg = mStates.begin();
for ( ; beg != mStates.end(); beg++)
{
beg->second->show();
}
cout<<endl;
};
void eraseState(StateType type)  //实现删除一个特效
{
auto result = mStates.find(type);
if(result != mStates.end())
mStates.erase(result);
}
protected:
char* mName;
map<StateType, absState*> mStates;
}; class concreteBuilding:public absBuilding
{
public:
concreteBuilding(char* name):absBuilding(name)
{
mStates[BUILDING] = new buildingState();
}
void upGrade()
{
auto result = mStates.find(UPGRADE);
if(result == mStates.end())
{
mStates[UPGRADE] = new upGradeState();
}
eraseState(BUILDING);    //升级的时候必须是建造过程已经结束,所以需要删掉“建筑”状态
eraseState(PRODUCTION);   //升级的时候不能进行生产
}
void production()
{
auto result = mStates.find(PRODUCTION);
if(result == mStates.end())
{
mStates[PRODUCTION] = new upGradeState();
}
eraseState(BUILDING);  //生产的时候必须已经建造完成
eraseState(UPGRADE);   //生产的时候不能升级
}
void injured()
{
auto result = mStates.find(INJURED);
if(result == mStates.end())
{
mStates[INJURED] = new fireState();
} }
void repair()
{
auto injuredVal = mStates.find(INJURED);
if(injuredVal == mStates.end())
return;
auto result = mStates.find(REPAIR);
if(result == mStates.end())
{
mStates[REPAIR] = new repairState();
} }
}; #endif

客户端代码main.cpp:

 #include <iostream>
#include "tank.h"
#include "building.h" using namespace std;
class SiegeTank; void main()
{
concreteBuilding cb("兵营");
cb.production();
cb.injured();
cb.repair();
cb.show();
return;
}

结果:

状态模式(state)C++实现的更多相关文章

  1. 【转】设计模式 ( 十七) 状态模式State(对象行为型)

    设计模式 ( 十七) 状态模式State(对象行为型) 1.概述 在软件开发过程中,应用程序可能会根据不同的情况作出不同的处理.最直接的解决方案是将这些所有可能发生的情况全都考虑到.然后使用if... ...

  2. 二十四种设计模式:状态模式(State Pattern)

    状态模式(State Pattern) 介绍允许一个对象在其内部状态改变时改变它的行为.对象看起来似乎修改了它所属的类. 示例有一个Message实体类,对它的操作有Insert()和Get()方法, ...

  3. 设计模式 ( 十七) 状态模式State(对象行为型)

    设计模式 ( 十七) 状态模式State(对象行为型) 1.概述 在软件开发过程中,应用程序可能会根据不同的情况作出不同的处理.最直接的解决方案是将这些所有可能发生的情况全都考虑到.然后使用if... ...

  4. 乐在其中设计模式(C#) - 状态模式(State Pattern)

    原文:乐在其中设计模式(C#) - 状态模式(State Pattern) [索引页][源码下载] 乐在其中设计模式(C#) - 状态模式(State Pattern) 作者:webabcd 介绍 允 ...

  5. 状态模式-State Pattern(Java实现)

    状态模式-State Pattern 在状态模式(State Pattern)中,类的行为是基于它的状态改变的.当一个对象的内在状态改变时允许改变其行为,这个对象看起来像是改变了其类. State接口 ...

  6. 北风设计模式课程---状态模式State(对象行为型)

    北风设计模式课程---状态模式State(对象行为型) 一.总结 一句话总结: 状态模式 具体状态的行为在具体的状态类中就解决,不用交给外部做判断.实质是将多条件判断弄成了多个类,在不同的类中做判断 ...

  7. 状态模式(State)-设计模式

    软件模式是将模式的一般概念应用于软件开发领域,即软件开发的 总体指导思路或参照样板.软件模式并非仅限于设计模式,还包括 架构模式.分析模式和过程模式等,实际上,在软件生存期的每一个阶段都存在着一些被认 ...

  8. 设计模式(十二):通过ATM取款机来认识“状态模式”(State Pattern)

    说到状态模式,如果你看过之前发布的重构系列的文章中的<代码重构(六):代码重构完整案例>这篇博客的话,那么你应该对“状态模式”并不陌生,因为我们之前使用到了状态模式进行重构.上一篇博客我们 ...

  9. 十一个行为模式之状态模式(State Pattern)

    定义: 当一个对象有多个状态,并且在每个状态下有不同的行为,可以使用状态模式来在其内部改变状态时改变其行为,而客户端不会察觉状态的改变,仍使用同样的方法或接口与对象进行交互. 结构图: Context ...

  10. 状态模式(State Pattern)

    当一个对象的内在状态改变时允许改变其行为,这个对象看起来像是改变了其类. 状态模式主要解决的是当控制一个对象状态的条件表达式过于复杂时的情况.把状态的判断逻辑转移到表示不同状态的一系列类中,可以把复杂 ...

随机推荐

  1. 【sqli-labs】 less17 POST - Update Query- Error Based - String (基于错误的更新查询POST注入)

    这是一个重置密码界面,查看源码可以看到username作了防注入处理 逻辑是先通过用户名查出数据,在进行密码的update操作 所以要先知道用户名,实际情况中可以注册用户然后实行攻击,这里先用admi ...

  2. 移动端出现弹出层body滚动

    $("#box").on("click",function(e){ e.stopPropagation(); e.preventDefault(); $(&qu ...

  3. [基准测试]----lmbench

    引言 要评价一个系统的性能,通常有不同的指标,相应的会有不同的测试方法和测试工具,一般来说为了确保测试结果的公平和权威性,会选用比较成熟的商业测试软件.但在特定情形下,只是想要简单比较不同系统或比较一 ...

  4. NOIP2016 DAY2 T3 愤怒的小鸟

    传送门 题目描述 Kiana 最近沉迷于一款神奇的游戏无法自拔. 简单来说,这款游戏是在一个平面上进行的. 有一架弹弓位于 (0,0)(0,0) 处,每次 Kiana 可以用它向第一象限发射一只红色的 ...

  5. 如何使用qtp12 utf进行功能测试

    首先,按照本博客的安装教程走的,右键管理员运行 接下来点击继续,这个界面只需要勾选到web即可 点击ok,开始运行 进入到主界面之后,file新建一个测试. 可以修改路径等等 点击create之后,出 ...

  6. 调用的方法里接收一个List<>类型的参数,里面是自定义的EC类, 我要通过反射构建这List对象

              public static object CreateGeneric(Type generic, Type innerType, params object[] args)     ...

  7. js实现cookie有效期至当次日凌晨

    实际开发中有要求用户一些行为每天一次,次日开始重新回复功能,一般前端都是通过cookie来记住用户的操作,然后进行判断当日是否还有机会,这时候需要给存储的cookie值一个有效期,让次日自动失效,重新 ...

  8. Spring Cloud Sleuth(十四)

    作用 再微服务中 服务调用服务很常见.服务中相互调用链路追踪的尤为重要,能够帮助我们再异常时分析出哪个服务出了异常.以及各个链路中相互调用所消耗时间,通过这些数据能够帮助我们分析出各个服务的性能瓶颈 ...

  9. 【ACM】NYOJ_506_洗澡_20130725

    洗澡时间限制:1000 ms  |  内存限制:65535 KB 难度:1描述 Mostrp是个爱干净的好少年. 有一次去澡堂洗澡时发现 澡堂的澡柜编号中没有出现过数字‘4’. Mostrp 感到很好 ...

  10. 数据库--ACID特性

    事务的ACID属性 原子性(Atomicity) 原子性是指事务是一个不可分割的工作单位,事务中的操作要么都发生,要么都不发生. 一致性(Consistency) 事务必须使数据库从一个一致性状态变换 ...