天天看点

State(状态)--对象行为型模式

State(状态)–对象行为型模式

一、意图

允许一个对象在其内部状态改变时改变它的行为。对象看起来似乎修改了它的类。

二、动机

1.在软件构建过程中,某些对象的状态如果改变,其行为也会随之而发生变化,比如文档处于只读状态,其支持的行为和读写状态支持的行为就可能完全不同。

2.如何在运行时根据对象的状态来透明地更改对象的行为?而不会为对象操作和状态转化之间引入紧耦合?

三、适用性

1.一个对象的行为取决于它的状态,并且它必须在运行时刻根据状态改变它的行为。

2.一个操作中含有庞大的多分支的条件语句,且这些分支依赖于该对象的状态。这个状态通常用一个或多个枚举常量表示。通常,有多个操作包含这一相同的条件结构。State模式将每一个条件分支放入一个独立的类中。这使得你可以根据对象自身的情况将对象的状态作为一个对象,者一对象可以不依赖于其他对象而独立的变化。

四、结构

State(状态)--对象行为型模式

五、效果

1.它将于特定状态相关的行为局部化,并且将不同状态的行为分割开来。 State模式将所有于一个特定的状态相关的行为都放入一个对象中。因为所有于状态相关的代码都存在于某一个State子类中,所以通过定义新的子类可以很容易的增加新的状态和转换。

2.它使得状态转化显式化。 当一个对象仅以内部数据值来定义当前状态时,其状态仅表现为对一些变量的赋值,这不够明确。为不同的状态引入独立的对象使得转换变得更加明确。而且,State对象可保证Context不会发生内部状态不一致的情况,因为从Context的角度看,状态转换是原子的——只需要重新绑定一个变量(即Context的State对象变量),而无需为对个变量赋值。

3.State对象可被共享。 如果State对象没有实例变量——即他们表示的状态完全以他们的类型来编码——那么各Context对象可以共享一个State对象。当状态以这种方式被共享时,他们必然没有内部状态,只有行为的轻量级对象。

六、实现

1.谁定义状态转换。 State模式不指定哪个一参与者定义状态转换准则。如果该准则是固定的,那么他们可在Context中完全实现。然而若让State子类自身指定他们的后继状态以及何时进行转换,通常更灵活更合适,这需要Context增加一个接口,让State对象显示地设定Context的当前状态。

用这种方法分散转换逻辑可言很容易地定义新的State子类来修改和扩展该逻辑。这样做的一个缺点是,一个State子类至少拥有一个其他子类信息,这就在个子类之间产生了实现依赖。

2.基于表的另一种方式。

3.创建和销毁State对象。 一个常见的值得考虑的实现上的权衡是,究竟是(1)仅需要State对象是才创建他们并随后销毁他们,还是(2)提前创建他们并且始终不销毁他们。

4.使用动态继承。

七、要点总结

1.State模式将所有于一个特定状态相关的行为都放入一个State的子类对象中,在对象状态切换时,切换相应的对象;但同时维持State的接口,这样实现了具体操作于状态转换之间的解耦。

2.为不同的状态引入不同的对象使得状态转换变得更加明确,而且可以保证不会出现状态不一致的情况,因为转换时原子性的——即要么彻底转换过来,要么不转换。

3.如果State对象没有实例变量,那么各个上下文可以共享一个State对象,从而节省对象开销。

八、相关模式

Flyweight模式解释了何时以及怎样共享状态对象。

状态对象通常是Singleton。

九、举例说明

人醉酒时的状态和平时的状态。

本文为李建忠设计模式视频的笔记以及《设计模式-可复用面向对象的软件的基础》和自己的部分见解

继续阅读