首页 > 代码库 > State - 状态模式

State - 状态模式

定义?
允许一个对象在其内部状态改变时改变它的行为。

案例
比如一个表示网络连接的类TCPConnection,它有不同的状态:连接已建立(Established),正在监听(Listening),连接已关闭(Closed)。当这个TCPConnection收到其他对象请求时,根据自身不同状态做出不同的响应。使用State模式处理这类问题的时候,引入一个TCPState类,它提供了所有正对TCPConnection不同状态操作的一个公共接口。


TCPConnection提供了一个传送数据的接口并处理改变状态的请求:
  1. Class TCPConnection
  2. {
  3. public:
  4. TCPConnection();
  5. void activeOPen();
  6. void passiveOpen();
  7. void close();
  8. void send();
  9. protected:
  10. friend class TCPState;
  11. void changeState(TCPState* state);
  12. private:
  13. TCPState* m_state;
  14. };
  15. TCPConnection::TCPConnection()
  16. {
  17. m_state = TCPClosed::instance();
  18. }
  19. void TCPConnection::activeOpen()
  20. {
  21. m_state->activeOpen();
  22. }
  23. void TCPConnection::passiveOpen()
  24. {
  25. m_state->passiveOpen();
  26. }
  27. void TCPConnection::close()
  28. {
  29. m_state->close();
  30. }
  31. void TCPConnection::send()
  32. {
  33. m_state->send();
  34. }
  35. void changeState(TCPState* state)
  36. {
  37. m_state = state;
  38. }
每一个TCPState操作都以一个TCPConnection实例作为参数,从而可以访问TCPConnection的数据和改变状态:
  1. class TCPState
  2. {
  3. public:
  4. virutal void activeOPen(TCPConnection*);
  5. virtual void passiveOpen(TCPConnection*)
  6. virtual void close(TCPConnection*);
  7. virtual void send(TCPConnection*);
  8. protected:
  9. void changeState(TCPConnection*, TCPState*);
  10. };
  1. class TCPEStablished : public TCPState
  2. {
  3. public:
  4. static TCPState* instance();
  5. virtual void close(TCPConnection* t)
  6. {
  7. changeState(t, TCPConnection::instance());
  8. }
  9. };
  1. class TCPListen : public TCPState
  2. {
  3. public:
  4. static TCPListen* instance();
  5. vritual void send(TCPConnection* t)
  6. {
  7. // send SYN, receive SYN, ACK, ect.
  8. changeState(t, TCPEStabiished::instance());
  9. }
  10. };
  1. class TCPClosed : public TCPState
  2. {
  3. public:
  4. virtual void activeOpen(TCPConnection* t)
  5. {
  6. // send SYN, receive SYN, ACK, ect.
  7. changeState(t, TCPEStablished::instance());
  8. }
  9. virtual void passiveOpen(TCPConnection* t)
  10. {
  11. // send FIN, receive ACK of FIN.
  12. changeState(t, TCPListen::instance());
  13. }
  14. };
适用性
  • 一个对象的行为取决于它的状态,并且它必须在运行时刻根据状态改变它的行为。
  • 一个操作中含有庞大的多分支的条件语句,并且这些分支依赖与该对象的状态。