您的位置:首页 > 编程语言 > Java开发

Java设计模式之状态模式

2013-12-01 23:37 323 查看
一、背景
最近系统的学习一下Java设计模式,下了2本电子书,《设计模式之禅》与《Head First 设计模式》,支持国产嘛,先看《设计模式之禅》,首先说一下对它的感觉,叙述比较简洁明了,举例很有趣味性、贴切,吸引人,有很多对比的例子(不采用设计模式和采用设计模式),对初学者来说还不错。有一个小遗憾就是:作者所画的类图有时并没有和代码对应。今天看到状态模式了,突然想来记录点什么,所以这篇博文就诞生了。

二、状态分析
还是拿作者的例子——电梯,电梯有四种动作:开门,关门,运行,停止。对应四种状态:门敞状态,门闭状态,运行状态,停止状态,它们之间的关系如下:

开门(open)关门(close)运行(run)停止(stop)
门敞状态nooknono
门闭状态oknookok
运行状态nononook
停止状态oknookno
三、画出类图

才刚开始学画类图了,采用的工具是starUML,如下:




四、代码
在类图基础上,利用starUML自动生成代码,然后再修改而成了。
1、环境封装类Context
public class Context {
private LiftState liftState;
public LiftState getLiftState() {
return this.liftState;
}

public void setListState(LiftState liftState) {
liftState.setContext(this);
this.liftState = liftState;
}

public void open() {
this.liftState.open();
}

public void close() {
this.liftState.close();
}

public void run() {
this.liftState.run();
}

public void stop() {
this.liftState.stop();
}
}


2、状态抽象类LiftState
public abstract class LiftState {
protected Context context;
public void setContext(Context _context) {
this.context = _context;
}

public abstract void open();

public abstract void close();

public abstract void run();

public abstract void stop();
}


3、四种状态类和状态池类OpenningState,ClosingState,RunningState,StoppingState,StatesPools

(1)OpenningState

public class OpenningState extends LiftState {
public void open() {
//已经打开了,不做任何操作
}

public void close() {
//打开状态,是可以关闭的
System.out.println("关闭电梯...");
super.context.setListState(StatesPool.closingState);
}

public void run() {
//开的时候,当然是不能跑的
}

public void stop() {
//开的时候,也没必要停
}
}


(2)ClosingState
public class ClosingState extends LiftState {
public void open() {
//关闭了当然是可以打开的
System.out.println("电梯打开");
super.context.setListState(StatesPool.openningState);
}

public void close() {
//已经关闭了

}

public void run() {
//关闭当然是可以运行的
System.out.println("电梯运行");
super.context.setListState(StatesPool.runningState);
}

public void stop() {
//关闭也可以停止的
System.out.println("电梯停止");
super.context.setListState(StatesPool.stoppingState);
}
}
(3)RunningState
public class RunningState extends LiftState {
public void open() {
//正在运行的时候不能开
}

public void close() {
//正在运行的时候不能关
}

public void run() {
//已经在运行了
}

public void stop() {
//运行时候,当然是可以停的
System.out.println("停止电梯...");
// 改变状态
super.context.setListState(StatesPool.stoppingState);
}
}


(4)StoppingState
public class StoppingState extends LiftState {
public void open() {
//停止状态下可以打开啦
System.out.println("电梯打开");
super.context.setListState(StatesPool.openningState);
}

public void close() {

}

public void run() {
//停止状态下可以继续运行了
System.out.println("电梯运行");
super.context.setListState(StatesPool.runningState);
}

public void stop() {

}
}


(5)StatesPools

public class StatesPool {
public static final OpenningState openningState = new OpenningState();
public static final ClosingState closingState = new ClosingState();
public static final RunningState runningState = new RunningState();
public static final StoppingState stoppingState = new StoppingState();
}
4、客户端调用类Client

public class Client {

public static void main(String[] args) {
Context context = new Context();
context.setListState(new ClosingState());

context.open();
context.close();
context.run();
context.stop();
context.open();

}
}
5、运行结果

电梯打开
关闭电梯...
电梯运行
停止电梯...
电梯打开


五、总结

行为与状态有对应关系,状态的切换伴随着相应的行为,都可以用状态模式了。另外抱怨51cto一句:再做好一点行不行啊,每次贴代码都要我重新选择语言,上面贴的代码都选了n次Java了,就不能帮我记住吗?
ps:代码地址http://down.51cto.com/data/1029676
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息