发布-订阅模式/观察者模式
发布-订阅模式也叫观察者模式,这是一个一对多的关系,可以多个订阅者订阅同一个事件,当事件触发时就会通知订阅者去执行订阅时绑定的程序;
我举个例子来解释一下:
A同学想在结婚的时候邀请好友B、C、D、E、F、G...来喝喜酒,这个邀请的名单其实就是订阅事件
class Person extends EventEmitter{ constructor(){ super(); }}let A= new Person();function drinkFn(){ console.log( `xxxx年xx月xx日来xx大酒店和我的喜酒!`)}A.on("结婚",drinkFn);
等到A同学要结婚的时候,他就会去通知他的好友XXX时间XX酒店过来喝酒,这个过程就是发布事件
A.emit("结婚");
以下是我的实现过程:
class EventEmitter { constructor(){ this._count=null; } //订阅事件 on(type,callBack,flag){ //创建_events对象 if(!this._events){ this._events=Object.create(null); } // 判断_events对象是否有type属性 if(this._events[type]){ if(flag){ this._events[type].unshift(callBack) }else{ this._events[type].push(callBack) } }else{ this._events[type]=[callBack] } //type如果不是newListener类型,则执行newListener对应的函数 if(type!=="newListener"){ this._events["newListener"]&&this._events["newListener"].forEach(fn=>{ fn(type,callBack); }) } // 超出最大绑定事件限制提示 if(this._events[type].length>=this.getMaxListeners()){ console.log("超出最大绑定事件限制") } } //订阅一次性事件 once(type,callBack,flag){ function warp(...argments){ callBack(...argments); this.removeListener(type,callBack) } warp.cb=callBack; this.on(type,warp,flag); } //发布事件 emit(type,...args){ if(this._events[type]){ this._events[type].forEach(fn => { fn.call(this,...args) }); } } // 获取当前type事件的数组对象 listeners(type){ return this._events[type]||[]; } // 订阅事件并在第一时间触发 prependListener(type,callBack){ this.on(type,callBack,true); } // 订阅一次性事件并在第一时间触发 prependOnceListener(type,callBack){ this.once(type,callBack,true); } // 获取当前实例所有的事件类型 eventNames(){ return Object.keys(this._events) } // 获取当前type事件类型的长度 listenerCount(type){ if(this._events[type]){ return this._events[type].length }else{ return 0 } } // 移除type事件所有的执行函数 removeListener(type,callBack){ if(this._events[type]){ this._events[type]=this._events[type].filter(fn=>{ return callBack!=fn&&fn.cb!=callBack }) } } // 移除实例上所有的事件 removeAllListeners(){ this._events=Object.create(null) } // 获取当前实例的最大事件绑定限制 getMaxListeners(){ return this._count ? this._count :EventEmitter.defaultMaxListeners; } // 设置当前实例的最大事件绑定限制 setMaxListeners(n){ this._count=n; } }// 设置默认的最大事件绑定限制EventEmitter.defaultMaxListeners=10;module.exports=EventEmitter;