状态模式
前言
状态模式(State),当一个对象的内在状态改变时允许改变其行为,这个对象看起来像是改变了其类。
状态模式主要解决的是当控制一个对象状态转换的条件表达式过于复杂时的情况。把状态的判断逻辑转移到表示不同状态的一系列类当中,可以把复杂的判断逻辑简单化。
一、State类,抽象状态类
1 public abstract class State
2 {
3 public abstract void WriteProgram(Work w);
4 }
二、具体的状态类
1 //上午工作状态
2 public class ForenoonState : State
3 {
4 public override void WriteProgram(Work w)
5 {
6 if (w.Hour < 12)
7 {
8 Console.WriteLine("当前时间:{0}点 上午工作。", w.Hour);
9 }
10 else
11 {
12 w.SetState(new NoonState());
13 w.WriteProgram();
14 }
15 }
16 }
17
18 public class NoonState : State
19 {
20 public override void WriteProgram(Work w)
21 {
22 if (w.Hour < 13)
23 {
24 Console.WriteLine("当前时间:{0}点 饿了,午饭:犯困,午休。", w.Hour);
25 }
26 else
27 {
28 w.SetState(new AfternoonState());
29 w.WriteProgram();
30 }
31 }
32 }
33 //下午工作状态
34 public class AfternoonState : State
35 {
36 public override void WriteProgram(Work w)
37 {
38 if (w.Hour < 17)
39 {
40 Console.WriteLine("当前时间:{0}点 .下午状态还不错,继续努力", w.Hour);
41 }
42 else
43 {
44 w.SetState(new EveningSate());
45 w.WriteProgram();
46 }
47 }
48 }
49 //晚上工作状态
50 public class EveningSate : State
51 {
52 public override void WriteProgram(Work w)
53 {
54 if (w.TaskFinished)
55 {
56 w.SetState(new RestState());
57 w.WriteProgram();
58 }
59 else
60 {
61 if (w.Hour < 21)
62 {
63 Console.WriteLine("当前时间:{0}点 .加班,累", w.Hour);
64 }
65 else
66 {
67 w.SetState(new SleepingState());
68 w.WriteProgram();
69 }
70 }
71 }
72 }
73 //睡眠状态
74 public class SleepingState : State
75 {
76 public override void WriteProgram(Work w)
77 {
78 Console.WriteLine("当前时间:{0}点 .睡着了", w.Hour);
79 }
80 }
81 //下班休息状态
82 public class RestState : State
83 {
84 public override void WriteProgram(Work w)
85 {
86 Console.WriteLine("当前时间:{0}点 .下班回家了", w.Hour);
87 }
88 }
三、工作类,此时没有了过长的分支判断语句
1 public class Work
2 {
3 private State current;
4 public Work()
5 {
6 //工作初始化为上午工作状态,即上午9点开始上班
7 current = new ForenoonState();
8 }
9 //'钟点'属性,状态转换的依据
10 public double Hour { get; set; }
11 //'任务完成'属性,是否能下班的依据
12 public bool TaskFinished { get; set; }
13 public void SetState (State s)
14 {
15 current = s;
16 }
17 public void WriteProgram()
18 {
19 current.WriteProgram(this);
20 }
21 }
四、客户端代码
1 class Program
2 {
3 static void Main(string[] args)
4 {
5 //紧急项目
6 Work p = new Work();
7 p.Hour = 9;
8 p.WriteProgram();
9 p.Hour = 10;
10 p.WriteProgram();
11 p.Hour = 12;
12 p.WriteProgram();
13 p.Hour = 13;
14 p.WriteProgram();
15 p.Hour = 14;
16 p.WriteProgram();
17 p.Hour = 17;
18 p.WriteProgram();
19
20 p.TaskFinished = false;
21 p.WriteProgram();
22 p.Hour = 19;
23 p.WriteProgram();
24 p.Hour = 22;
25 p.WriteProgram();
26
27 Console.ReadKey();
28 }
29 }
总结
1、状态模式的好处是将与特定状态相关的行为局部化,并且将不同状态的行为分割开来。
2、状态模式将特定的状态相关的行为都放入一个对象中,由于所有与状态相关的代码都存在于某个ConcreteState中,所以通过定义新的子类可以很容易地增加新的状态和转换。这样就能消除庞大的条件分支语句。
3、状态模式通过把各种状态逻辑分布到state的子类之间,来减少相互间的依赖。
4、当一个对象的行为取决于它的状态,并且它必须在运行时刻根据状态改变它的行为时,就可以考虑使用状态模式了。
参考书籍:大话设计模式