js design patterns - state mode

State mode

Allows an object to change its behavior when its internal state is changed, the object will appear to change its class.

Simple explanation:

  • The first portion means that the state of the package into separate categories, and delegates the request to the current state of the object, when the object's internal state changes, the change will bring a different behavior.
  • The second part is from the customer's point of view, the object we use, have very different behavior in different states, the object appears to be from a different class instantiated from the fact that the use of commission Effect.

Now give more of an online example, it is an example of true lamp (do not bother, please be patient to look down)

// 首先定义了一个Light类
class Light {
  // 定义一个状态变量
  constructor(){
    this.state = 'off'
  }
  // 定义一个改变状态的方法
  change(){
    if(this.state === 'off'){
      console.log('开灯')
      this.state = 'on'
    } else {
      console.log('关灯')
      this.state = 'off'
    }
  }
}
// 创建实例
let light = new Light()
// 调用方法
light.change()

Dangdang this we have written a state machine, logic is simple yet careful, it seems there are so unassailable point. The BUT , you know that is not true, life is not so much wishful. With the progress of mankind, demand is not (de) off (cuo) into (jin) step (chi) (● '◡' ●), so the emergence of a new lamp, which lights can be powerful, first click weak light, glare click again, and then point colorful light, and then point emmm off.

According to our logic to write the above, it may stimulate:

  • First, in violation of the principle of opening and closing, each change must change change () method, making the process becomes unstable
  • State switch is not obvious, you can not understand a glance how many states there are
  • Switching the relationship between the state, but to change () method in adding if, else statement is change () method is more difficult to read and maintain

then what should we do? How to sing a song to a "new lights have emerged, how can stagnation", ha ha, so the state model to the ~ ~ ~

Examples lamp because too boring, so I changed one example, but it means the same thing drops:

  // 单曲循环类
  class SingleCycle{
    constructor(self){
      this._self = self
    }
    modeSwitch(){
      console.log('现在是单曲循环')
      this._self.setState( this._self.listCirculation )
    }
  }
  // 列表循环类
  class ListCirculation{
    constructor(self){
      this._self = self
    }
    modeSwitch(){
      console.log('现在是列表循环')
      this._self.setState( this._self.sequentialPlay )
    }
  }
  // 顺序播放类
  class SequentialPlay{
    constructor(self){
      this._self = self
    }
    modeSwitch(){
      console.log('现在是顺序播放')
      this._self.setState( this._self.shufflePlay )
    }
  }
  // 随机播放类
  class ShufflePlay{
    constructor(self){
      this._self = self
    }
    modeSwitch(){
      console.log('现在是随机播放')
      this._self.setState( this._self.singleCycle )
    }
  }
  // 音乐类
  class Music{
    constructor(){
      // 为每个状态都创建一个状态对象
      this.singleCycle = new SingleCycle(this)
      this.listCirculation = new ListCirculation(this)
      this.sequentialPlay = new SequentialPlay(this)
      this.shufflePlay = new ShufflePlay(this)
      // 定义初始状态为顺序播放
      this.currState = this.sequentialPlay
    }
    // 切换播放模式
    changeMode(){
      this.currState.modeSwitch()
    }
    // 下一次点击时的播放状态
    setState(newState){
      this.currState = newState;
    }
  }
  // 实例化音乐类
  let music = new Music()
  // 调用切换播放模式方法
  music.changeMode()

Well, we adapt to this completion, if you do not have to rip out, good, if you are ignorant lost, look down:

  1. First we define the four state class SingleCycle(单曲循环), ListCirculation(列表循环), SequentialPlay(顺序播放),ShufflePlay(随机播放)
  2. Each class defines a state variable _selfto receive the Music(音乐类)pass over this, there is a method modeSwitch(状态更改), to be played next time for changing the state of
  3. Then define a Music(音乐类)first inside for each state have created a state of the object, but also defines a variable currStateto record the state of the next click.
  4. The last two methods is Music (Musical) inside defined changeMode(切换播放模式), setState(下一次点击时的播放状态). When we click on the toggle mode when, in changeMode(切换播放模式)good condition prior to the class definition to call modeSwitch(状态更改)to call method, mode switching is completed at the same time (music class) in Music setState(下一次点击时的播放状态)ways to make changes to the state switch to a different time ensuring a single click mode.

As can be seen by the above method:

  1. We can Music(音乐类)clearly know how many in a state of total, while Music(音乐类)no longer perform any substantial operation, but by this.currState.modeSwitch()going to the execution state of the object currently held
  2. Law switching state is well defined in advance for each class in the state, in Music(音乐类)no state of a switch and associated conditional branch statement

Quietly he said, the above method also wide in order to re-perfect little Yo


A small expansion

Have a Through the above description we learned each state class modeSwitch()method, which means that every time we add state have to write a class method, the question is, people are not err too? So the blanket will inevitably lose it!

Then do some small optimization:

// 定义一个State类
class State{
  constructor(self){
    this._self = self
  }
  modeSwitch(){
   throw new Error( '父类的 modeSwitch 方法必须被重写' )
  }
}

// 状态类(举一个为例)

// 单曲循环类(继承State类)
class SingleCycle extends State{
  modeSwitch(){
    console.log('现在是单曲循环')
    this._self.setState( this._self.listCirculation )
  }
}

Well finished, when one day we forgot to write method, it is possible to quickly locate the error


Currently the state model for understanding so much later have a new understanding will continue to update, and slipped slipped (~ ¯ ▽ ¯) ~

Guess you like

Origin www.cnblogs.com/loveyt/p/11403784.html