状态模式
- 状态模式的关键是把事物的每种状态都封装成单独的类,跟此种状态有关的行为都被封装在这个类内部;当内部状态改变时,会带来不同的行为变化;
电灯开关的例子
var offLightState = function(light) {
this.light = light;
};
offLightState.prototype.buttonWasPressed = function() {
console.log('weakLightState');
this.light.setState(this.light.weakLightState);
};
var weakLightState = function(light) {
this.light = light;
};
weakLightState.prototype.buttonWasPressed = function() {
console.log('strongLightState');
this.light.setState(this.light.strongLightState);
};
var strongLightState = function(light) {
this.light = light;
};
strongLightState.prototype.buttonWasPressed = function() {
console.log('offLightState');
this.light.setState(this.light.offLightState);
};
var Light = function() {
this.offLightState = new offLightState(this);
this.weakLightState = new weakLightState(this);
this.strongLightState = new strongLightState(this);
this.button = null;
};
Light.prototype.init = function() {
var button = document.createElement('button');
self = this;
this.button = document.body.appendChild(button);
this.button.innerHTML = '开关';
this.currState = this.offLightState;
this.button.onclick = function() {
self.currState.buttonWasPressed();
}
};
Light.prototype.setState = function(newState) {
this.currState = newState;
};
var light = new Light();
light.init();
JS版本的状态机器
- JS是无类的,没有规定让状态对象一定要从类中创建而来;此外JS可以非常方便地使用委托技术,并不需要要事先让一个对象持有另一个对象;
var delegate = function(client, delegation) {
return {
buttonWasPressed: function() {
return delegation.buttonWasPressed.apply(client, arguments);
}
}
};
var FSM = {
off: {
buttonWasPressed: function() {
console.log('on');
this.currState = this.onState;
}
},
on: {
buttonWasPressed: function() {
console.log('off');
this.currState = this.offState;
}
}
};
var Light = function() {
this.offState = delegate(this, FSM.off);
this.onState = delegate(this, FSM.on);
this.button = null;
};
Light.prototype.init = function() {
var button = document.createElement('button');
self = this;
this.button = document.body.appendChild(button);
this.button.innerHTML = '开关';
this.currState = this.offState;
this.button.onclick = function() {
self.currState.buttonWasPressed();
}
};
var light = new Light();
light.init();
另一个例子
var MarryState = function () {
var _currentState = {};
var states = {
jump: function () {
console.log('jump');
},
move: function () {
console.log('move');
},
shoot: function () {
console.log('shoot');
},
squat: function () {
console.log('squat');
}
};
var Action = {
changeState: function () {
var arg = arguments;
_currentState = {};
if(arg.length) {
for(var i = 0, l = arg.length; i < l; i++) {
_currentState[arg[i]] = true;
}
}
return this;
},
gose: function () {
console.log('gose');
for(var i in _currentState) {
states[i] && states[i]();
}
return this;
}
};
return {
change: Action.changeState,
gose: Action.gose
}
}
var marry = new MarryState();
marry.change('jump', 'shoot').gose().gose()
.change('shoot').gose();
状态模式和策略模式
- 相同点是都有一个上下文,一些策略或者状态类,上下文吧请求委托给这些类来执行;
- 区别是策略模式中各个策略类之间是平等又平行的,他们之间没有任何联系;客户必须熟知这些策略类的作用以便随时主动切换算法;
- 状态模式中,状态和状态对应的行为是早已封装好的,之间的切换也是规定好的,改变行为发生在状态模式内部;客户并不需要了解这些细节;
对于分支优化
- 工厂方法模式: 创建性模式,目的是创建对象;
- 状态模式: 行为性模式,核心是对象状态的控制来决定表现行为,状态之间不能替换;
- 策略模式: 行为性模式,核心是算法,由于每种算法处理的业务逻辑相同,可以互相替换;
适配器模式
- 将一个类(对象)的接口转化为另一个接口,解决接口不匹配的问题;
- 设计之初不会考虑,用于补救的模式;
适配异类框架
参数适配
function doSomeThing(obj) {
var _adapter = {
name: 'jinks',
titile: 'enginner',
age: 24,
....
}
for(var i in _adapter) {
_adapter[i] = obj[i] || _adapter[i];
}
//doSome
}
数据适配
- 将数组转化为易于理解的对象格式;
- 服务器与客户端接口数据的适配;