`

状态模式(State)

 
阅读更多
状态模式:允许对象在内部状态改变时改变它的行为,对象看起来好像修改了它的类.

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

要点:
1.状态模式允许一个对象基于内部状态而拥有不同的行为
2.和程序状态机(PSM)不同,状态模式用类代表状态
3.Context会将行为委托给当前状态对象
4.通过将每个状态封装进一个类,我们把以后需要做的任何改变局部化了
5.状态模式和策略模式有相同的类图,但它们的意图不同
6.策略模式通常会用行为或算法来配置Context类
7.状态模式允许Context随着状态的改变而改变行为
8.状态转换可以由State类或Context类控制
9.使用状态模式通常会导致设计中类的数目大量增加//确实如此...
10.状态类可以被多个Context实例共享



由于2个类的相互引用,导致很多类都要写进cpp,代码虽然比较多,但逻辑并不复杂
GameState.h
#ifndef GAMESTATE_H
#define GAMESTATE_H

enum State{
    ADDCOINS,
    PLAYGAME,
    BADGAME,
    GOODGAME,
    GAMEOVER
};

class GameState{
public:
    virtual void addCoins()=0;
    virtual void playGame()=0;
    virtual void badGame()=0;
    virtual void goodGame()=0;
    virtual void gameOver()=0;
};

#endif // GAMESTATE_H



AddCoinsState.h
#ifndef ADDCOINSSTATE_H
#define ADDCOINSSTATE_H
#include "GameState.h"
#include "GameMachine.h"
#include <iostream>
using namespace std;

class GameMachine;
class AddCoinsState:public GameState{
private:
    GameMachine* mMachine;
public:
    AddCoinsState(GameMachine* machine);
    void addCoins();
    void playGame();
    void badGame();
    void goodGame();
    void gameOver();
};

#endif // ADDCOINSSTATE_H


AddCoinsState.cpp
#include "AddCoinsState.h"

AddCoinsState::AddCoinsState(GameMachine *machine){
    mMachine = machine;
}

void AddCoinsState::addCoins(){
    mMachine->setCount(mMachine->getCount()+2);
    cout << "add a coin" << endl;
    mMachine->setState(mMachine->getPlayGameState());
}

void AddCoinsState::playGame(){
    cout << "please add a coin" << endl;
}

void AddCoinsState::badGame(){
    cout << "no coin" << endl;
}

void AddCoinsState::goodGame(){
    cout << "no coin" << endl;
}

void AddCoinsState::gameOver(){
    cout << "no coin" << endl;
}



PlayGameState.h
#ifndef PLAYGAMESTATE_H
#define PLAYGAMESTATE_H
#include "GameState.h"
#include "GameMachine.h"

class GameMachine;
class PlayGameState:public GameState{
private:
    GameMachine* mMachine;
    bool mFlag;
public:
    PlayGameState(GameMachine* machine);
    void addCoins();
    void playGame();
    void badGame();
    void goodGame();
    void gameOver();
};

#endif // PLAYGAMESTATE_H



PlayGameState.cpp
#include "PlayGameState.h"
#include <stdlib.h>

PlayGameState::PlayGameState(GameMachine *machine){
    mMachine = machine;
    mFlag = false;
}

void PlayGameState::addCoins(){
    mMachine->setCount(mMachine->getCount()+2);
}

void PlayGameState::playGame(){
    srand(time(0));
    while(mMachine->getCount()>0){
        if(not mFlag){
            int game = rand()%10+1;//1-10
            if(game>=8){
                mFlag = true;//只给一次good game的机会
                mMachine->setState(mMachine->getGoodGameState());
                mMachine->goodGame();
            }
        }
        mMachine->setState(mMachine->getBadGameState());
        mMachine->badGame();
    }
    mMachine->setState(mMachine->getGameOverState());
    mMachine->gameOver();
}

void PlayGameState::badGame(){
    cout << "playing" << endl;
}

void PlayGameState::goodGame(){
    cout << "playing" << endl;
}

void PlayGameState::gameOver(){
    cout << "playing" << endl;
}



BadGameState.h
#ifndef BADGAMESTATE_H
#define BADGAMESTATE_H
#include "GameState.h"
#include "GameMachine.h"

class GameMachine;
class BadGameState:public GameState{
private:
    GameMachine* mMachine;
public:
    BadGameState(GameMachine* machine);
    void addCoins();
    void playGame();
    void badGame();
    void goodGame();
    void gameOver();
};
#endif // BADGAMESTATE_H


BadGameState.cpp
#include "BadGameState.h"

BadGameState::BadGameState(GameMachine *machine){
    mMachine = machine;
}

void BadGameState::addCoins(){
    mMachine->setCount(mMachine->getCount()+2);
}

void BadGameState::playGame(){
    badGame();
}

void BadGameState::badGame(){
    mMachine->setState(mMachine->getPlayGameState());
    mMachine->setCount(mMachine->getCount()-1);
    cout << "a bad game,coin-1:" << mMachine->getCount() << endl;
}

void BadGameState::goodGame(){
    badGame();
}

void BadGameState::gameOver(){
    badGame();
}



GoodGameState.h
#ifndef GOODGAMESTATE_H
#define GOODGAMESTATE_H
#include "GameState.h"
#include "GameMachine.h"

class GameMachine;
class GoodGameState:public GameState{
private:
    GameMachine* mMachine;
public:
    GoodGameState(GameMachine* machine);
    void addCoins();
    void playGame();
    void badGame();
    void goodGame();
    void gameOver();
};
#endif // GOODGAMESTATE_H



GoodGameState.cpp
#include "GoodGameState.h"

GoodGameState::GoodGameState(GameMachine *machine){
    mMachine = machine;
}

void GoodGameState::addCoins(){
    mMachine->setCount(mMachine->getCount()+2);
}

void GoodGameState::playGame(){
    goodGame();
}

void GoodGameState::badGame(){
    goodGame();
}

void GoodGameState::goodGame(){
    mMachine->setState(mMachine->getPlayGameState());
    mMachine->setCount(mMachine->getCount()+1);
    cout << "a good game,coin+1:" << mMachine->getCount() << endl;
}

void GoodGameState::gameOver(){
    goodGame();
}



GameOverState.h
#ifndef GAMEOVERSTATE_H
#define GAMEOVERSTATE_H
#include "GameState.h"
#include "GameMachine.h"

class GameMachine;
class GameOverState:public GameState{
private:
    GameMachine* mMachine;
public:
    GameOverState(GameMachine* machine);
    void addCoins();
    void playGame();
    void badGame();
    void goodGame();
    void gameOver();
};
#endif // GAMEOVERSTATE_H



GameOverState.cpp
#include"GameOverState.h"

GameOverState::GameOverState(GameMachine* machine){
    mMachine = machine;
}
void GameOverState::addCoins(){
    mMachine->setCount(mMachine->getCount()+2);
}
void GameOverState::playGame(){
    gameOver();
}
void GameOverState::badGame(){
    gameOver();
}
void GameOverState::goodGame(){
    gameOver();
}
void GameOverState::gameOver(){
    cout << "game over!" << endl;
}



GameMachine.h
#ifndef GAMEMACHINE_H
#define GAMEMACHINE_H
#include "GameState.h"
#include "AddCoinsState.h"
#include "PlayGameState.h"
#include "BadGameState.h"
#include "GoodGameState.h"
#include "GameOverState.h"
#include <assert.h>
#include <iostream>
using namespace std;

class GameMachine{
private:
    State mState;
    int mCount;
    GameState* addCoinsState;
    GameState* playGameState;
    GameState* badGameState;
    GameState* goodGameState;
    GameState* gameOverState;
    GameState* gameState;//default
public:
    GameMachine(int count);
    void addCoins(){
        gameState->addCoins();
        cout << "add a coins:" << mCount << endl;
    }
    void playGame(){
        gameState->playGame();
    }
    void badGame(){
        gameState->badGame();
    }
    void goodGame(){
        gameState->goodGame();
    }
    void gameOver(){
        gameState->gameOver();
    }
    void setState(GameState* state){
        gameState = state;
    }
    int getCount()const{
        return mCount;
    }
    void setCount(int count){
        mCount = count;
    }
    GameState* getAddCoinsState(){
        return addCoinsState;
    }
    GameState* getPlayGameState(){
        return playGameState;
    }
    GameState* getBadGameState(){
        return badGameState;
    }
    GameState* getGoodGameState(){
        return goodGameState;
    }
    GameState* getGameOverState(){
        return gameOverState;
    }
};

#endif // GAMEMACHINE_H



GameMachine.cpp
#include "GameMachine.h"

GameMachine::GameMachine(int count){
    assert(count>=0);
    cout << "add " << count << " coins" << endl;
    mCount = count;
    addCoinsState = new AddCoinsState(this);
    playGameState = new PlayGameState(this);
    badGameState = new BadGameState(this);
    goodGameState = new GoodGameState(this);
    gameOverState = new GameOverState(this);
    if(count>0){
        mState = PLAYGAME;
        gameState = new PlayGameState(this);
    }else{
        mState = GAMEOVER;
        gameState = new GameOverState(this);
    }
}



main.cpp
#include "GameMachine.h"

int main(){
    GameMachine *machine = new GameMachine(5);
    machine->addCoins();
    machine->playGame();
}



add 5 coins
add a coins:7//投一个币加2次机会
a bad game,coin-1:6
a good game,coin+1:7
a bad game,coin-1:6
a bad game,coin-1:5
a bad game,coin-1:4
a bad game,coin-1:3
a bad game,coin-1:2
a bad game,coin-1:1
a bad game,coin-1:0
game over!


一份关于rtsp的实现
#include <iostream>
using namespace std;

class RTSPState
{
public:
    RTSPState(){}
    virtual ~RTSPState(){}
    virtual bool processDescribe()
    {
        cout << "无法处理describe" << endl;
        return false;
    }
    virtual bool processSetup()
    {
        cout << "无法处理setup" << endl;
        return false;
    }
    virtual bool processPlay()
    {
        cout << "无法处理play" << endl;
        return false;
    }
    virtual bool processTeardown()
    {
        cout << "无法处理teardown" << endl;
        return false;
    }
};

class DescribeState:public RTSPState
{
public:
    bool processSetup()
    {
        cout << "处理setup" << endl;
        return true;
    }
};

class SetupState:public RTSPState
{
public:
    bool processPlay()
    {
        cout << "处理play" << endl;
        return true;
    }
};

class PlayState:public RTSPState
{
public:
    bool processTeardown()
    {
        cout << "处理teardown" << endl;
        return true;
    }
};

class TeardownState:public RTSPState
{
public:
    bool processDescribe()
    {
        cout << "处理describe" << endl;
        return true;
    }
};

class RTSPLink
{
public:
    RTSPLink()
    {
        mDescribeState = new DescribeState;
        mSetupState = new SetupState;
        mPlayState = new PlayState;
        mTeardownState = new TeardownState;
        mRtspState = mTeardownState;
    }

    ~RTSPLink()
    {
        mRtspState = NULL;
        if(mDescribeState!=NULL)
        {
            delete mDescribeState;
            mDescribeState = NULL;
        }
        if(mSetupState!=NULL)
        {
            delete mSetupState;
            mSetupState = NULL;
        }
        if(mPlayState!=NULL)
        {
            delete mPlayState;
            mPlayState = NULL;
        }
        if(mTeardownState!=NULL)
        {
            delete mTeardownState;
            mTeardownState = NULL;
        }
    }

    void setState(RTSPState* rtspState)
    {
        mRtspState= rtspState;
    }

    RTSPState* getDescribeState()
    {
        return mDescribeState;
    }

    RTSPState* getSetupState()
    {
        return mSetupState;
    }

    RTSPState* getPlayState()
    {
        return mPlayState;
    }

    RTSPState* getTeardownState()
    {
        return mTeardownState;
    }

    bool processDescribe()
    {
        if(mRtspState->processDescribe())
        {
            setState(mDescribeState);
            return true;
        }
        setState(mTeardownState);
        return false;
    }

    bool processSetup()
    {
        if(mRtspState->processSetup())
        {
            setState(mSetupState);
            return true;
        }
        setState(mTeardownState);
        return false;
    }

    bool processPlay()
    {
        if(mRtspState->processPlay())
        {
            setState(mPlayState);
            return true;
        }
        setState(mTeardownState);
        return false;
    }

    bool processTeardown()
    {
        if(mRtspState->processTeardown())
        {
            setState(mTeardownState);
            return true;
        }
        setState(mTeardownState);
        return false;
    }

private:
    RTSPState *mDescribeState;

    RTSPState *mSetupState;

    RTSPState *mPlayState;

    RTSPState *mTeardownState;

    RTSPState *mRtspState;
};

int main()
{
    RTSPLink * rtspLink = new RTSPLink;
    rtspLink->processDescribe();
    rtspLink->processSetup();
    rtspLink->processPlay();
    rtspLink->processTeardown();
    cout << "设置playstate" << endl;
    rtspLink->setState(rtspLink->getPlayState());
    rtspLink->processDescribe();
}

处理describe
处理setup
处理play
处理teardown
设置playstate
无法处理describe
  • 大小: 73.4 KB
分享到:
评论

相关推荐

    状态模式 State Pattern

    ### 状态模式(State Pattern) #### 概念与定义 状态模式是一种行为设计模式,它允许对象在其内部状态改变时改变其行为,使对象看起来像是修改了它的类。该模式通过引入一个代表各种状态的类以及一个行为随着这些...

    设计模式之状态模式State

    状态模式通常包含三个主要角色:Context(上下文)、State(抽象状态)和ConcreteState(具体状态)。 上下文是拥有状态的对象,它定义了与该状态相关的接口,并负责在适当的时候将请求委托给相应的状态对象处理。...

    每天感悟总结-状态模式State

    2009-03-10模式State:一个事件(消息)引起环境或数据的变化,可能导致状态变化,于是处理流程改变,这里的状态是把处理流程分成了很多阶段,通过状态机来根据传来的事件(消息)引发状态转换,管理状态属性和状态行为,...

    设计模式C++学习之状态模式(State)

    状态模式是一种行为设计模式,它允许对象在内部状态改变时改变其行为,对象看起来似乎修改了它的类。这种模式常用于处理对象的状态变化,并且使代码结构清晰,易于维护。 在C++中,状态模式通常包含以下几个关键...

    设计模式之状态模式(State)

    状态模式是一种行为设计模式,它使对象能够在内部状态改变时改变其行为,看起来好像改变了它的类。这种模式常用于处理对象在不同状态下表现各异的情况,避免了复杂的条件语句,提高了代码的可读性和可维护性。 在...

    Android的状态机模式StateMachine与State

    在博文《Android的状态机模式StateMachine与State》中,作者可能会详细介绍如何创建和使用这两种组件。通常,状态机的实现会涉及到以下步骤: 1. **定义状态接口或抽象类**:创建一个State接口或抽象类,其中包含...

    设计模式之状态模式(State Pattern)

    状态模式是一种行为设计模式,它使你能在运行时改变对象的行为。在状态模式中,一个对象的状态变化会导致其行为的变化,这种变化不是通过改变对象的类来实现的,而是通过改变对象的状态。这个模式的核心是封装可能...

    Head First 设计模式 (十) 状态模式(State pattern) C++实现

    状态模式是一种行为设计模式,它允许对象在内部状态改变时改变其行为,对象看起来似乎修改了它的类。这种模式常用于处理对象的状态变化,并且根据不同的状态,对象的行为也相应地变化。在C++中实现状态模式,我们...

    JackChan1999#Java-Degisn-Patterns#状态模式-State Pattern1

    状态模式-State Pattern状态模式-State Pattern【学习难度:,使用频率:】状态模式-State Pattern处理对象的多种状态及其相互

    《设计模式》实战---状态模式(State Pattern)

    在《设计模式》实战---状态模式(State Pattern)这篇文章中,作者可能详细探讨了以下关键点: 1. **模式定义**:状态模式允许对象在内部状态改变时改变其行为,对象看起来好像修改了它的类。这通过将每个状态封装...

    设计模式 - 状态模式(C++实例)

    在C++中实现状态模式,我们通常会定义一个抽象状态类(State),它声明了所有可能的状态行为。然后,创建一系列具体状态类(ConcreteState)来实现这些行为。每个具体状态类代表一种特定的状态,并且在内部维护当前...

    状态模式(State Pattern)是一种行为设计模式

    状态模式(State Pattern)是一种行为设计模式,它允许对象在内部状态改变时改变其行为,对象看起来似乎修改了它的类。这种模式将一个对象的行为分解为各个独立的状态,并且每个状态都封装在自己的类中,使得对象在...

    设计模式State模式源码

    State模式在实际使用中比较多,适合"状态的切换".因为我们经常会使用If elseif else 进行状态切换, 如果针对状态的这样判断切换反复出现,我们就要联想到是否可以采取State模式了. 不只是根据状态,也有根据属性.如果...

    状态模式代码示例

    在提供的压缩包`state.zip`中,很可能包含一个简单的状态模式实现,可能包括`Context`、`AbstractState`和几个`ConcreteState`类。这些类的结构可能是这样的: ```java // Context public class Context { ...

    C#面向对象设计模式纵横谈(22):(行为型模式) State 状态模式

    标题和描述均提到了"C#面向对象设计模式"中的State状态模式,这表明文章的核心内容是围绕State模式在C#编程语言中的应用展开。State模式是一种行为设计模式,旨在允许对象在其内部状态改变时,其行为也能相应地改变...

    c++状态模式

    状态模式是一种行为设计模式,它允许对象在内部状态改变时改变其行为,对象看起来似乎修改了它的类。在C++中,状态模式通常通过定义一系列的类来表示各种状态,并用一个上下文类来管理这些状态的切换。下面将详细...

    管理订单状态,该上状态机吗?轻量级状态机COLA StateMachine保姆级入门教程.doc

    在订单状态管理中,状态机模式是一种常用的解决方案,但是在实际项目中,状态机的使用率并没有想象中那么高。笔者在电商领域进行后端开发时,发现了状态机的重要性,但是在使用 Spring StateMachine 时,发现了它的...

    java 设计模式之状态模式

    状态模式是一种行为设计模式,它允许对象在内部状态改变时改变其行为,看起来好像对象改变了它的类。在Java中,状态模式通常通过定义不同的状态类和一个上下文类来实现,其中上下文类持有状态对象并调用其方法来响应...

    设计模式:状态模式TCPConnection案例

    状态模式是一种行为设计模式,它使你能在运行时改变对象的行为。在TCP连接中,状态模式的应用尤为常见,因为TCP连接在不同的阶段会有不同的行为,比如建立连接、数据传输、断开连接等。下面我们将详细探讨这个模式...

Global site tag (gtag.js) - Google Analytics