手写代码

发布-订阅机制

最简单的发布订阅就是addEventListener,先监听click,之后点击元素触发事件。

可以看到两个关键的动作:事件的监听(订阅)和事件的触发(发布)

手写发布订阅模型

  • on():负责注册事件的监听器,指定事件触发时的回调函数。
  • emit():负责触发事件,可以通过传参使其在触发的时候携带数据 。
  • off():负责监听器的删除。
class myEventEmitter {
  constructor() {
    this.eventMap = {};
  }
  // type 这里就代表事件的名称
  on(type, handler) {
    // hanlder 必须是一个函数,如果不是直接报错
    if (!(handler instanceof Function)) {
      throw new Error("哥 你错了 请传一个函数");
    }
    // 判断 type 事件对应的队列是否存在
    if (!this.eventMap[type]) {
      this.eventMap[type] = [];
    }
    this.eventMap[type].push(handler);
  }
  emit(type, params) {
    // 假设该事件是有订阅的(对应的事件队列存在)
    if (this.eventMap[type]) 
      this.eventMap[type].forEach((handler, index) => {
        handler(params);
      });
    }
  }
  off(type, handler) {
    if (this.eventMap[type]) {
      this.eventMap[type].splice(this.eventMap[type].indexOf(handler) >>> 0, 1);
    }
  }
}

使用无符号右移,-1 无符号右移的结果为 4294967295,这个数足够大,不会对原队列造成影响,否则如果indexOf返回-1再调用 splice 就会将队列中最后一个函数删除掉了

posted @ 2021-06-12 18:49  __前端工程师  阅读(139)  评论(0)    收藏  举报