随笔 - 12, 文章 - 0, 评论 - 5, 引用 - 0
数据加载中……

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

前几天由于忙工作上的事情,每天加班到10点左右才回家,回到家就没有再开电脑更新东西,今天早了一些回家,开始继续更新东西,今天要写的是状态模式,哦,对于一个没有状态的人来说,写状态模式,不知道会写成什么样子,反正是一起讨论用嘛,能把我所知道的清楚表达出来已经很心满意足啦。在理解状态模式的时候,我总觉得它和策略模式很像很像,有人说它们是孪生兄弟,那我们现在看看状态模式到底是一个什么样的东西。

状态模式是对象的一个行为模式,它允许一个对象在其内部状态改变的时候改变其行为,这个对象看上去就像改了了它的类一样。

下图是关于红绿灯转换的一个实现类图,具体的转换是这样子的,在初始的情况下,设定一个灯的状态,比如是绿灯,那么灯的下一个状态则是黄灯,紧接着是红灯,然后再是绿灯,依次循环;通过改变灯的状态,改变其行为。

下面是这个类图的实现代码:

package com.plabmedia.state;

public interface LightState {

/**
* 打印当前的状态
*/
public void print(Light light);

}

package com.plabmedia.state;

public class RedLight implements LightState{

@Override
public void print(Light light) {
System.out.println("current state is red");
light.setState(new GreenLight());
}

}

package com.plabmedia.state;

public class YellowLight implements LightState{

@Override
public void print(Light light) {
System.out.println("current state is yellow");
light.setState(new RedLight());
}

}

package com.plabmedia.state;

public class GreenLight implements LightState {

@Override
public void print(Light light) {
System.out.println("current state is green");
light.setState(new YellowLight());
}

}

package com.plabmedia.state;

public class Light {

private LightState state;

public LightState getState() {
return state;
}

public void setState(LightState state) {
this.state = state;
}

public void print(){
state.print(this);
}

public Light(LightState state){
this.state = state;
}

}

package com.plabmedia.state;

public class Client {

public static void main(String args[]){
Light light = new Light(new GreenLight());
light.print();
light.print();
light.print();
light.print();
light.print();
light.print();
}

}

运行结果:

current state is green
current state is yellow
current state is red
current state is green
current state is yellow
current state is red

上面是对状态模式一个小小的实现,这个实现也仅仅是认识级的,在我们实际应用中,如果用到状态模式,应该比这个要负责的多,只是基本的结构是相似的。那我们下面针对状态模式做一些讨论。

1.在什么情况下使用状态模式:

  • 一个对象的行为依赖于它所处的状态,对象的行为必须随着其状态的改变而改变;
  • 需要多多重条件转移语句进行演化的时候,可以把每个分支封装成一个状态类;现在写代码的时候,我是不太喜欢用条件转移语句,特别是最好的那个else语句,我觉得它承担的东西太多了,前面不满足的情况它都要来处理,凭什么啊。
2.状态模式要注意的地方:
  • 谁来定义状态的变化:客户端还是状态内部决定?这要看当时应用的环境,如果状态的变化是固定的,我觉得可以再客户端进行设定;如果状态的变化依赖于前一个状态,比如在工作流系统中,当前状态是依赖于前一个状态的,这需要状态内部来觉得。
  • 状态对象创建时机:需要的时候创建?还是事先创建好所有的对象,供需要的时候调用?这要分系统需要来决定,如果一个系统,状态变化的顺序固定,不那么频繁,则可以在需要的时候创建所需要的对象;否则,对于频繁变化的状态,从性能上将,还是首先创建好各个状态对象,供需要时调用。
  • 可以把环境类传到具体的状态类中,状态类在需要的时候调用环境类,比如示例中的样子,其实在每个状态类里面,也可以直接调用环境类的print方法,这样看来,Client只需要初始化环境类,然后就可以看到它的状态在不停地变化。
3.状态模式与策略模式的区别:
我粗俗的说一些,从我的理解的基础上,二者之间的区别在于状态模式在集体作战,而策略模式是单兵作战,怎么说呢?状态模式因为其内部状态的改变会有不同的行为出现,而对于策略模式,只要客户端选中了一种策略,在整个生命周期内,都是这种策略。所以,在区分使用状态模式和策略模式的时候,主要是看系统有没有状态的变化,如果系统在整个生命周期内,只有一种状态,那很好,选择策略模式;如果系统在整个过程中,状态多样性,那需要选择状态模式。
先写这么多吧,好没有状态啊,希望大家都抽出时间一起讨论,说说自己对状态模式的看法。

posted on 2012-07-21 22:23 拼搏 阅读(1026) 评论(0)  编辑  收藏


只有注册用户登录后才能发表评论。


网站导航: