js状态模式
状态模式,当一个对象的内在状态改变时允许改变其行为,这个对象看起来是改变了其类。
状态模式主要解决的是当控制一个对象状态转换的条件表达式过于复杂时的情况。把状态的判断逻辑转移到表示不同状态的一系列类当中,可以把复杂的判断逻辑简化。
既然状态者模式是对已有对象的状态进行抽象,则自然就有抽象状态者类和具体状态者类,而原来已有对象需要保存抽象状态者类的引用,通过调用抽象状态者的行为来改变已有对象的行为。经过上面的分析,状态者模式的结构图也就很容易理解了,具体结构图如下图示。

从上图可知,状态者模式涉及以下三个角色:
- Account类:维护一个State类的一个实例,该实例标识着当前对象的状态。
- State类:抽象状态类,定义了一个具体状态类需要实现的行为约定。
- SilveStater、GoldState和RedState类:具体状态类,实现抽象状态类的每个行为。
C#状态模式:
namespace 状态模式
{
class Program
{
static void Main(string[] args)
{
//紧急项目
Work emergencyProjects = new Work();
emergencyProjects.Hour = ;
emergencyProjects.WriteProgram();
emergencyProjects.Hour = ;
emergencyProjects.WriteProgram();
emergencyProjects.Hour = ;
emergencyProjects.WriteProgram();
emergencyProjects.Hour = ;
emergencyProjects.WriteProgram();
emergencyProjects.Hour = ;
emergencyProjects.WriteProgram();
emergencyProjects.Hour = ; //emergencyProjects.WorkFinished = true;
emergencyProjects.TaskFinished = false; emergencyProjects.WriteProgram();
emergencyProjects.Hour = ;
emergencyProjects.WriteProgram();
emergencyProjects.Hour = ;
emergencyProjects.WriteProgram(); Console.Read();
}
} //抽象状态
public abstract class State
{
public abstract void WriteProgram(Work w);
} //上午工作状态
public class ForenoonState : State
{
public override void WriteProgram(Work w)
{
if (w.Hour < )
{
Console.WriteLine("当前时间:{0}点 上午工作,精神百倍", w.Hour);
}
else
{
w.SetState(new NoonState());
w.WriteProgram();
}
}
} //中午工作状态
public class NoonState : State
{
public override void WriteProgram(Work w)
{
if (w.Hour < )
{
Console.WriteLine("当前时间:{0}点 饿了,午饭;犯困,午休。", w.Hour);
}
else
{
w.SetState(new AfternoonState());
w.WriteProgram();
}
}
} //下午工作状态
public class AfternoonState : State
{
public override void WriteProgram(Work w)
{
if (w.Hour < )
{
Console.WriteLine("当前时间:{0}点 下午状态还不错,继续努力", w.Hour);
}
else
{
w.SetState(new EveningState());
w.WriteProgram();
}
}
} //晚间工作状态
public class EveningState : State
{
public override void WriteProgram(Work w)
{
if (w.TaskFinished)
{
w.SetState(new RestState());
w.WriteProgram();
}
else
{
if (w.Hour < )
{
Console.WriteLine("当前时间:{0}点 加班哦,疲累之极", w.Hour);
}
else
{
w.SetState(new SleepingState());
w.WriteProgram();
}
}
}
} //睡眠状态
public class SleepingState : State
{
public override void WriteProgram(Work w)
{
Console.WriteLine("当前时间:{0}点 不行了,睡着了。", w.Hour);
}
} //下班休息状态
public class RestState : State
{
public override void WriteProgram(Work w)
{
Console.WriteLine("当前时间:{0}点 下班回家了", w.Hour);
}
} //工作
public class Work
{
private State current;
public Work()
{
current = new ForenoonState();
} private double hour;
public double Hour
{
get { return hour; }
set { hour = value; }
} private bool finish = false;
public bool TaskFinished
{
get { return finish; }
set { finish = value; }
} public void SetState(State s)
{
current = s;
} public void WriteProgram()
{
current.WriteProgram(this);
}
}
}
状态者模式的应用场景
在以下情况下可以考虑使用状态者模式。
- 当一个对象状态转换的条件表达式过于复杂时可以使用状态者模式。把状态的判断逻辑转移到表示不同状态的一系列类中,可以把复杂的判断逻辑简单化。
- 当一个对象行为取决于它的状态,并且它需要在运行时刻根据状态改变它的行为时,就可以考虑使用状态者模式。
javascript版本的状态机:
var Light = function(){
this.currState = FSM.off; //设置当前状态
this.button = null;
};
Light.prototype.init = function(){
var button = document.createElement('button'),
self = this;
button.innerHTML = '已关灯';
this.button = document.body.appendChild(button);
this.button.onclick = function(){
self.currState.buttonWasPressed.call(self); //把请求委托给FSM状态机
}
};
var FSM = {
off:{
buttonWasPressed:function(){
console.log('关灯');
this.button.innerHTML = '下一次按我是开灯';
this.currState = FSM.on;
}
},
on:{
buttonWasPressed:function(){
console.log('开灯');
this.button.innerHTML = '下一次按我是关灯';
this.currState = FSM.off;
}
}
};
var light = new Light();
light.init();
实际项目中的其他状态机:
var FSM = {
walk:{
attack:function(){
console.log('攻击');
},
defense:function(){
console.log('防御');
},
jump:function(){
console.log('跳跃');
}
},
attack:{
walk:function(){
console.log('攻击的时候不能行走');
},
defense:function(){
console.log('攻击的时候不能防御');
},
jump:function(){
console.log('攻击的时候不能跳跃');
}
}
};
状态模式的电灯程序:
var Light = function(){
this.currState = FSM.off; //设置当前状态
};
Light.prototype.init = function(){
self = this;
this.button.onclick = function(){
self.currState.buttonWasPressed.call(self); //把请求委托给FSM状态机
}
};
var FSM = {
off:{
buttonWasPressed:function(){
console.log('弱光');
this.currState = FSM.weak;
}
},
weak:{
buttonWasPressed:function(){
console.log('强光');
this.currState = FSM.strong;
}
},
strong:{
buttonWasPressed:function(){
console.log('关灯');
this.currState = FSM.off;
}
}
};
var light = new Light();
light.init();
状态模式-水的三态变化
用js模拟物理现象,实现水的三态变化,初中物理课我们都学过,物质具有三态变化,气态 -> 液态 -> 固态 或者 固态 -> 液态 -> 气态,但是不可以气态 -> 固态,或者固态 -> 气态,是需要经过液态过度的,否则就违反了自然规律。所以这种状态的变化非常适合用状态模式来实现。代码如下:
var Water = function(){
this.currState = FSM.gas; //设置当前状态
this.h3 = null;
};
Water.prototype.init = function(){
var button1 = document.createElement('button'),
button2 = document.createElement('button'),
button3 = document.createElement('button'),
h3 = document.createElement('h3'),
self = this;
button1.innerHTML = '100度以上';
button1.onclick = function(){
self.currState.gas.call(self);
}
button2.innerHTML = '0-100度';
button2.onclick = function(){
self.currState.liquid.call(self);
}
button3.innerHTML = '0度以下';
button3.onclick = function(){
self.currState.solid.call(self);
}
document.body.appendChild(button1);
document.body.appendChild(button2);
document.body.appendChild(button3);
this.h3 = document.body.appendChild(h3);
};
var FSM = {
gas:{ //气态
liquid:function(){
console.log('液态');
this.h3.innerHTML = '液态';
this.currState = FSM.liquid;
},
solid:function(){
console.log('气态不能变化为固态');
alert('气态不能变化为固态');
}
},
liquid:{ //液态
solid:function(){
console.log('固态');
this.h3.innerHTML = '固态';
this.currState = FSM.solid;
},
gas:function(){
console.log('气态');
this.h3.innerHTML = '气态';
this.currState = FSM.gas;
}
},
solid:{ //固态
gas:function(){
console.log('固态不能变化为气态');
alert('固态不能变化为气态');
},
liquid:function(){
console.log('液态');
this.h3.innerHTML = '液态';
this.currState = FSM.liquid;
}
}
};
var water = new Water();
water.init();
js状态模式的更多相关文章
- JS常用的设计模式(17)—— 状态模式
状态模式主要可以用于这种场景 1 一个对象的行为取决于它的状态 2 一个操作中含有庞大的条件分支语句 回想下街头霸王的游戏. 隆有走动,攻击,防御,跌倒,跳跃等等多种状态,而这些状态之间既有联系又互相 ...
- js策略模式vs状态模式
一.策略模式 1.定义:把一些小的算法,封装起来,使他们之间可以相互替换(把代码的实现和使用分离开来)2.利用策略模式实现小方块缓动 html代码: <div id="containe ...
- js设计模式——5.状态模式
js设计模式——5.状态模式 代码演示 /*js设计模式——状态模式*/ // 状态(红灯,黄灯,绿灯) class State { constructor(color) { this.color = ...
- 8.js模式-状态模式
1. 状态模式 var offLightState = function(light){ this.light = light; } offLightState.prototype.buttonWas ...
- 大熊君说说JS与设计模式之------状态模式State
一,总体概要 1,笔者浅谈 状态模式,又称状态对象模式(Pattern of Objects for States),状态模式是对象的行为模式. 状态模式主要解决的是当控制一个对象状态的条件表达式过于 ...
- JS设计模式(13)状态模式
什么是状态模式? 定义:将事物内部的每个状态分别封装成类,内部状态改变会产生不同行为. 主要解决:对象的行为依赖于它的状态(属性),并且可以根据它的状态改变而改变它的相关行为. 何时使用:代码中包含大 ...
- js 设计模式——状态模式
状态模式 允许一个对象在其内部状态改变时改变它的行为,对象看起来似乎修改了它的类. 简单的解释一下: 第一部分的意思是将状态封装成独立的类,并将请求委托给当前的状态对象,当对象的内部状态改变时,会带来 ...
- js之状态模式
level01:电灯程序 <!DOCTYPE html> <html lang="en"> <head> <meta charset=&q ...
- Javascript设计模式理论与实战:状态模式
在软件开发中,很大部分时候就是操作数据,而不同数据下展示的结果我们将其抽象出来称为状态,我们平时开发时本质上就是对应用程序的各种状态进行切换并作出相应处理.状态模式就是一种适合多种状态场景下的设计模式 ...
随机推荐
- maven仓库添加本地jar
一.将jar添加到本地仓库的做法: 以下面pom.xml依赖的jar包为例: 实际项目中pom.xml依赖写法: <dependency> <groupId>org.sprin ...
- Pycharm中目前用到的快捷键
1.批量注释:Ctrl+/ 2.缩进\不缩进:Tab\Shift+Tab 3.运行:Ctrl+Shift+F10 4.撤销\反撤销:Ctrl+z\Ctrl+shift+z 5.当光标在代码中间,如何回 ...
- Python3.6全栈开发实例[002]
2.判断用户传入的对象(字符串.列表.元组)长度是否大于5. li = [11,22,33,44,55,66,77,88,99,000,111,222] def func2(lst): if len( ...
- python模块学习(四)
re模块 就其本质而言,正则表达式(或 RE)是一种小型的.高度专业化的编程语言,(在Python中)它内嵌在Python中,并通过 re 模块实现.正则表达式模式被编译成一系列的字节码,然后由用 C ...
- Axure快捷键
基本快捷键: 打开:Ctrl + O 新建:Ctrl + N 保存:Ctrl + S 退出:Alt + F4 打印:Ctrl + P 查找:Ctrl + F 替换:Ctrl + H 复制:Ctrl + ...
- 模拟美式橄榄球比赛数据(R)
获得和清洗数据: 1.从网络上抓取数据 year<- url<-paste("http://sports.yahoo.com/nfl/stats/byteam?group=Off ...
- windows安装pywin32
下载旧版 https://sourceforge.net/projects/pywin32/files/pywin32/ 下载新版 https://github.com/mhammond/pywin3 ...
- spark学习(2)--hadoop安装、配置
环境: 三台机器 ubuntu14.04 hadoop2.7.5 jdk-8u161-linux-x64.tar.gz (jdk1.8) 架构: machine101 :名称节点.数据节点.Secon ...
- 谷歌机器学习速成课程---3降低损失 (Reducing Loss):梯度下降法
迭代方法图(图 1)包含一个标题为“计算参数更新”的华而不实的绿框.现在,我们将用更实质的方法代替这种华而不实的算法. 假设我们有时间和计算资源来计算 w1 的所有可能值的损失.对于我们一直在研究的回 ...
- [转] 我所经历的IBM SOA与系统整合
2006年,一汽大众新上来一位总经理,新加坡人,整个一国际背景高端管理人才,是德国人和中国人博弈后取得的胜利. 一汽大众过去是从总部到区域到终端一体化的大盘管理模式,很僵化很粘稠,不利用快速反应.于是 ...