Nodejs核心模块之Events

核心模块之Events

通过EventEmitter类实现事件统一管理

events与EventEmitter

  • node.js是基于事件驱动的异步操作架构,内置events模块
  • events模块提供了EventEmitter类
  • node.js中很多内置核心模块集成EventEmitter

EventEmitter常见Api

  • on
    • 添加实现被触发时调用的回调函数
const EventEmitter = require('events')
const ev = new EventEmitter()
// on 
ev.on('事件1', () => {
  console.log('事件1执行了---2')
})
ev.on('事件1', () => {
  console.log('事件1执行了')
})
  • emit
    • 出发事件,按照注册的顺序同步调用每个事件监听器
// emit触发
ev.emit('事件1')
  • once
    • 添加当事件在注册之后首次被触发时调用的回调函数
ev.once('事件1', () => {
  console.log('事件1执行了')
})
ev.once('事件1', () => {
  console.log('事件1执行了--2')
})

ev.emit('事件1')
ev.emit('事件1')
  • off
    • 移除特定的监听器
let cbFn = (...args) => {
  console.log(args)
}
ev.on('事件1', cbFn) 
ev.emit('事件1')
// 移除
ev.off('事件1', cbFn)
ev.emit('事件1', 1, 2, 3)

发布订阅

  • 缓存队列,存放订阅者消息
  • 具有增加和删除订阅的能力
  • 状态改变时通知所有订阅者执行监听
  • 发布订阅存在一个调度中心,而观察者中是不存在的
  • 状态发生改变时,发布订阅无须主动通知订阅者
    在这里插入图片描述
class PubSub{
  constructor() {
    this._events = {}
  }

  // 注册
  subscribe(event, callback) {
    if (this._events[event]) {
      // 如果当前 event 存在,所以我们只需要往后添加当前次监听操作
      this._events[event].push(callback)
    } else {
      // 之前没有订阅过此事件
      this._events[event] = [callback]
    }
  }

  // 发布
  publish(event, ...args) {
    const items = this._events[event]
    if (items && items.length) {
      items.forEach(function (callback) {
        callback.call(this, ...args)
      })
    }
  }
}

let ps = new PubSub()
ps.subscribe('事件1', () => {
  console.log('事件1执行了')
})
ps.subscribe('事件1', () => {
  console.log('事件1执行了---2')
})

ps.publish('事件1')
ps.publish('事件1')

EventEmitter模拟

function MyEvent () {
  // 准备一个数据结构用于缓存订阅者信息
  this._events = Object.create(null)
}

MyEvent.prototype.on = function (type, callback) {
  // 判断当前次的事件是否已经存在,然后再决定如何做缓存
  if (this._events[type]) {
    this._events[type].push(callback)
  } else {
    this._events[type] = [callback]
  }
}

MyEvent.prototype.emit = function (type, ...args) {
  if (this._events && this._events[type].length) {
    this._events[type].forEach((callback) => {
      callback.call(this, ...args)
    })
  }
}

MyEvent.prototype.off = function (type, callback) {
  // 判断当前 type 事件监听是否存在,如果存在则取消指定的监听
  if (this._events && this._events[type]) {
    this._events[type] = this._events[type].filter((item) => {
      return item !== callback && item.link !== callback
    })
  }
}

MyEvent.prototype.once = function (type, callback) {
  let foo = function (...args) {
    callback.call(this, ...args)
    this.off(type, foo)
  }
  foo.link = callback
  this.on(type, foo)
}

let ev = new MyEvent()

let fn = function (...data) {
  console.log('事件1执行了', data)
}

ev.once('事件1', fn)
// ev.off('事件1', fn)
ev.emit('事件1', '前')
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值