状态模式.cpp
# include <iostream>
# include <memory>
using namespace std;
namespace ns1
{ class Monster { public : enum MonsterState { MonS_Fer, MonS_Worr, MonS_Fear, MonS_Dead } ; private : int m_life; MonsterState m_status; public : Monster ( int life, MonsterState status = MonS_Fer) : m_life ( life) , m_status ( status) { } public : void Attacked ( int power) { m_life -= power; switch ( m_status) { case MonS_Fer: if ( m_life > 400 ) { cout << "monster " << power << " hurt, attact!" << endl; } else if ( m_life > 100 ) { cout << "monster " << power << " hurt, attact, help!" << endl; m_status = MonS_Worr; } else if ( m_life > 0 ) { cout << "monster " << power << " hurt, MonS_Fear, run!" << endl; m_status = MonS_Fear; } else { cout << "monster " << power << " hurt, dead!" << endl; m_status = MonS_Dead; } break ; case MonS_Worr: if ( m_life > 100 ) { cout << "monster " << power << " hurt, attact, help!" << endl; } else if ( m_life > 0 ) { cout << "monster " << power << " hurt, MonS_Fear, run!" << endl; m_status = MonS_Fear; } else { cout << "monster " << power << " hurt, dead!" << endl; m_status = MonS_Dead; } break ; case MonS_Fear: if ( m_life > 0 ) { cout << "monster " << power << " hurt, run!" << endl; } else { cout << "monster " << power << " hurt, dead!" << endl; m_status = MonS_Dead; } break ; default : cout << "monster dead, cannot be attacketed!" << endl; break ; } } } ;
} namespace ns2
{ class Monster ; class MonsterStatus { public : virtual ~ MonsterStatus ( ) { } virtual void Attacked ( int power, Monster * const mainobj) = 0 ; } ; class MonsterStatus_Feroc : public MonsterStatus { public : void Attacked ( int power, Monster * const mainobj) override { cout << "MonsterStatus_Feroc, attackt!" << endl; } } ; class MonsterStatus_Worr : public MonsterStatus { public : void Attacked ( int power, Monster * const mainobj) override { cout << "MonsterStatus_Worr, attackt, help!" << endl; } } ; class MonsterStatus_Fear : public MonsterStatus { public : void Attacked ( int power, Monster * const mainobj) override { cout << "MonsterStatus_Fear, run!" << endl; } } ; class MonsterStatus_Dead : public MonsterStatus { public : void Attacked ( int power, Monster * const mainobj) override { cout << "dead!" << endl; } } ; class Monster { int m_life; shared_ptr< MonsterStatus> m_pState; public : Monster ( int life, const shared_ptr< MonsterStatus> & pState = make_shared < MonsterStatus_Feroc> ( ) ) : m_life ( life) , m_pState ( pState) { } public : void Attacked ( int power) { int orglife = m_life; m_life -= power; if ( orglife > 400 ) { if ( m_life > 400 ) { m_pState-> Attacked ( power, this ) ; } else if ( m_life > 100 ) { m_pState. reset ( new MonsterStatus_Worr ( ) ) ; m_pState-> Attacked ( power, this ) ; } else if ( m_life > 0 ) { m_pState. reset ( new MonsterStatus_Fear ( ) ) ; m_pState-> Attacked ( power, this ) ; } else { m_pState. reset ( new MonsterStatus_Dead ( ) ) ; m_pState-> Attacked ( power, this ) ; } } else if ( orglife > 100 ) { if ( m_life > 100 ) { m_pState-> Attacked ( power, this ) ; } else if ( m_life > 0 ) { m_pState. reset ( new MonsterStatus_Fear ( ) ) ; m_pState-> Attacked ( power, this ) ; } else { m_pState. reset ( new MonsterStatus_Dead ( ) ) ; m_pState-> Attacked ( power, this ) ; } } else if ( orglife > 0 ) { if ( m_life > 0 ) { m_pState-> Attacked ( power, this ) ; } else { m_pState. reset ( new MonsterStatus_Dead ( ) ) ; m_pState-> Attacked ( power, this ) ; } } else { m_pState-> Attacked ( power, this ) ; } } } ;
} namespace ns3
{ class Monster ; class MonsterStatus { public : virtual ~ MonsterStatus ( ) { } virtual void Attacked ( int power, Monster * const mainobj) = 0 ; } ; class MonsterStatus_Feroc : public MonsterStatus { public : void Attacked ( int power, Monster * const mainobj) override ; } ; class MonsterStatus_Worr : public MonsterStatus { public : void Attacked ( int power, Monster * const mainobj) override ; } ; class MonsterStatus_Fear : public MonsterStatus { public : void Attacked ( int power, Monster * const mainobj) override ; } ; class MonsterStatus_Dead : public MonsterStatus { public : void Attacked ( int power, Monster * const mainobj) override ; } ; class Monster { int m_life; shared_ptr< MonsterStatus> m_pState; public : Monster ( int life, const shared_ptr< MonsterStatus> & pState = make_shared < MonsterStatus_Feroc> ( ) ) : m_life ( life) , m_pState ( pState) { } public : void Attacked ( int power) { m_pState-> Attacked ( power, this ) ; } public : int GetLife ( ) const { return m_life; } void SetLife ( int life) { m_life = life; } shared_ptr< MonsterStatus> getCurrentState ( ) const { return m_pState; } void setCurrentState ( const shared_ptr< MonsterStatus> & pState) { m_pState = pState; } } ; void MonsterStatus_Feroc :: Attacked ( int power, Monster * const mainobj) { int orglife = mainobj-> GetLife ( ) ; if ( ( orglife - power) > 400 ) { mainobj-> SetLife ( orglife - power) ; cout << "MonsterStatus_Feroc, attackt!" << endl; } else { mainobj-> setCurrentState ( make_shared < MonsterStatus_Worr> ( ) ) ; mainobj-> Attacked ( power) ; } } void MonsterStatus_Worr :: Attacked ( int power, Monster * const mainobj) { int orglife = mainobj-> GetLife ( ) ; if ( ( orglife - power) > 100 ) { mainobj-> SetLife ( orglife - power) ; cout << "MonsterStatus_Worr, attackt, help!" << endl; } else { mainobj-> setCurrentState ( make_shared < MonsterStatus_Fear> ( ) ) ; mainobj-> Attacked ( power) ; } } void MonsterStatus_Fear :: Attacked ( int power, Monster * const mainobj) { int orglife = mainobj-> GetLife ( ) ; if ( ( orglife - power) > 0 ) { mainobj-> SetLife ( orglife - power) ; cout << "MonsterStatus_Fear, run!" << endl; } else { mainobj-> setCurrentState ( make_shared < MonsterStatus_Dead> ( ) ) ; mainobj-> Attacked ( power) ; } } void MonsterStatus_Dead :: Attacked ( int power, Monster * const mainobj) { int orglife = mainobj-> GetLife ( ) ; if ( orglife > 0 ) { mainobj-> SetLife ( orglife - power) ; } cout << "dead!" << endl; }
} namespace ns4
{ class Monster ; class MonsterStatus { public : virtual ~ MonsterStatus ( ) { } virtual void Attacked ( int power, Monster * const mainobj) = 0 ; } ; class MonsterStatus_Feroc : public MonsterStatus { public : void Attacked ( int power, Monster * const mainobj) override ; public : static shared_ptr< MonsterStatus> getInstance ( ) { static shared_ptr< MonsterStatus> instance ( new MonsterStatus_Feroc ( ) ) ; return instance; } } ; class MonsterStatus_Worr : public MonsterStatus { public : void Attacked ( int power, Monster * const mainobj) override ; public : static shared_ptr< MonsterStatus> getInstance ( ) { static shared_ptr< MonsterStatus> instance ( new MonsterStatus_Worr ( ) ) ; return instance; } } ; class MonsterStatus_Fear : public MonsterStatus { public : void Attacked ( int power, Monster * const mainobj) override ; public : static shared_ptr< MonsterStatus> getInstance ( ) { static shared_ptr< MonsterStatus> instance ( new MonsterStatus_Fear ( ) ) ; return instance; } } ; class MonsterStatus_Dead : public MonsterStatus { public : void Attacked ( int power, Monster * const mainobj) override ; public : static shared_ptr< MonsterStatus> getInstance ( ) { static shared_ptr< MonsterStatus> instance ( new MonsterStatus_Dead ( ) ) ; return instance; } } ; class Monster { int m_life; shared_ptr< MonsterStatus> m_pState; public : Monster ( int life, const shared_ptr< MonsterStatus> & pState = MonsterStatus_Feroc :: getInstance ( ) ) : m_life ( life) , m_pState ( pState) { } public : void Attacked ( int power) { m_pState-> Attacked ( power, this ) ; } public : int GetLife ( ) const { return m_life; } void SetLife ( int life) { m_life = life; } shared_ptr< MonsterStatus> getCurrentState ( ) const { return m_pState; } void setCurrentState ( const shared_ptr< MonsterStatus> & pState) { m_pState = pState; } } ; void MonsterStatus_Feroc :: Attacked ( int power, Monster * const mainobj) { int orglife = mainobj-> GetLife ( ) ; if ( ( orglife - power) > 400 ) { mainobj-> SetLife ( orglife - power) ; cout << "MonsterStatus_Feroc, attackt!" << endl; } else { mainobj-> setCurrentState ( MonsterStatus_Worr :: getInstance ( ) ) ; mainobj-> Attacked ( power) ; } } void MonsterStatus_Worr :: Attacked ( int power, Monster * const mainobj) { int orglife = mainobj-> GetLife ( ) ; if ( ( orglife - power) > 100 ) { mainobj-> SetLife ( orglife - power) ; cout << "MonsterStatus_Worr, attackt, help!" << endl; } else { mainobj-> setCurrentState ( MonsterStatus_Fear :: getInstance ( ) ) ; mainobj-> Attacked ( power) ; } } void MonsterStatus_Fear :: Attacked ( int power, Monster * const mainobj) { int orglife = mainobj-> GetLife ( ) ; if ( ( orglife - power) > 0 ) { mainobj-> SetLife ( orglife - power) ; cout << "MonsterStatus_Fear, run!" << endl; } else { mainobj-> setCurrentState ( MonsterStatus_Dead :: getInstance ( ) ) ; mainobj-> Attacked ( power) ; } } void MonsterStatus_Dead :: Attacked ( int power, Monster * const mainobj) { int orglife = mainobj-> GetLife ( ) ; if ( orglife > 0 ) { mainobj-> SetLife ( orglife - power) ; } cout << "dead!" << endl; }
} int main ( )
{
# if 0 using namespace ns1; Monster monster ( 500 , Monster:: MonS_Fer) ; cout << "Monster, MonS_Fer, 500 blood!" << endl; monster. Attacked ( 20 ) ; monster. Attacked ( 100 ) ; monster. Attacked ( 200 ) ; monster. Attacked ( 170 ) ; monster. Attacked ( 100 ) ; monster. Attacked ( 100 ) ;
# endif # if 0 using namespace ns2; Monster monster ( 500 ) ; cout << "Monster, MonS_Fer, 500 blood!" << endl; monster. Attacked ( 20 ) ; monster. Attacked ( 100 ) ; monster. Attacked ( 200 ) ; monster. Attacked ( 170 ) ; monster. Attacked ( 100 ) ; monster. Attacked ( 100 ) ;
# endif # if 0 using namespace ns3; Monster monster ( 500 ) ; cout << "Monster, MonS_Fer, 500 blood!" << endl; monster. Attacked ( 20 ) ; monster. Attacked ( 100 ) ; monster. Attacked ( 200 ) ; monster. Attacked ( 170 ) ; monster. Attacked ( 100 ) ; monster. Attacked ( 100 ) ;
# endif # if 1 using namespace ns4; Monster monster ( 500 ) ; cout << "Monster, MonS_Fer, 500 blood!" << endl; monster. Attacked ( 20 ) ; monster. Attacked ( 100 ) ; monster. Attacked ( 200 ) ; monster. Attacked ( 170 ) ; monster. Attacked ( 100 ) ; monster. Attacked ( 100 ) ;
# endif cout << "Over!\n" ; return 0 ;
}