推荐答案
-- -------------------- ---- ------- ----- ------------ - ------------- - ----------- - --- - ------------- --------- - -- ------------------------- - ---------------------- - --- - -------------------------------------- - --------------- -------- - -- ------------------------ - --------------------------------------- -- - ------------------ --- - - -------------- --------- - -- ------------------------- - ------- - -------------- ------ ----------------------- ------ - ---------------------- - -------------------------------- -- -- --- ---------- - - -- ---- ----- ------- - --- --------------- ----- ---------- - --------- -- - ----------------------- --------- -- ----- ---------- - --------- -- - ------------------------ -------- - --------------------- ------------ --------------------- ------------ ----------------------- ------- --------- -- --- -------- ------ ------ -------- ------ ------ --------------------------------- ----------------------- ------ ------ ------------- -- --- -------- ----- ------ ---------- ---------------------- ----------------------------- ------ --- ------- ------- -- -------
本题详细解读
发布-订阅模式的概念
发布-订阅模式(Publish-Subscribe Pattern)是一种消息传递模式,它允许组件(发布者)发布消息,而无需知道哪些组件(订阅者)会接收这些消息。订阅者订阅感兴趣的消息类型,当发布者发布相应类型的消息时,订阅者会收到通知。这种模式实现了组件之间的松耦合,使得系统更易于扩展和维护。
实现思路
- 事件存储: 使用一个对象
this.events
来存储事件及其对应的回调函数列表。键为事件名称(eventName
),值为回调函数数组。 on
方法(订阅):- 接收两个参数:事件名称
eventName
和回调函数callback
。 - 如果
this.events
中不存在eventName
的键,则创建一个新的空数组。 - 将
callback
添加到this.events[eventName]
数组中。
- 接收两个参数:事件名称
emit
方法(发布):- 接收一个参数:事件名称
eventName
和可变数量的参数...args
,这些参数会传递给回调函数。 - 检查
this.events
中是否存在eventName
的键。 - 如果存在,则遍历
this.events[eventName]
数组中的所有回调函数,并使用...args
调用每一个回调函数。
- 接收一个参数:事件名称
off
方法(取消订阅):- 接收两个参数:事件名称
eventName
和可选的回调函数callback
。 - 检查
this.events
中是否存在eventName
的键,如果不存在则直接返回。 - 如果未传入
callback
, 则删除this.events[eventName]
所有订阅的事件。 - 如果传入了
callback
,则过滤this.events[eventName]
中的回调函数,将不等于callback
的函数保留下来,以此移除指定的订阅。
- 接收两个参数:事件名称
代码详解
class EventEmitter
: 定义一个EventEmitter
类来封装发布-订阅逻辑。constructor()
: 初始化this.events
为空对象。on(eventName, callback)
: 实现了订阅功能,将回调函数添加到指定事件的回调数组中。emit(eventName, ...args)
: 实现了发布功能,遍历并执行指定事件的所有回调函数。off(eventName, callback)
: 实现了取消订阅功能,移除指定事件或指定事件下的指定回调函数。
示例代码解释
示例代码创建了一个 EventEmitter
实例,并使用 on
方法订阅了 message
事件的两个回调函数 logMessage
和 logWarning
。 当使用 emit('message', 'Hello, world!')
发布消息时,两个回调函数都会被调用。之后调用 off
移除 logMessage
, 再次调用 emit
只会执行 logWarning
, 最后调用off('message')
移除所有 message
事件的订阅,后续调用 emit
不会执行任何订阅事件。