观察者模式

2026 年 2 月 18 日 星期三
5

观察者模式

观察者模式(Observer Pattern)是一种行为型设计模式,实现了一种类似“订阅”的机制。它包含两个核心角色:观察者(订阅消息、接收通知并执行操作)和被观察者(维护观察者列表、在状态变化时通知所有观察者)。两者通过一对多关系实现解耦:被观察者只负责“通知”,观察者只负责“响应”。

在真实世界中可以类比为:商店老板(被观察者)记录客户(观察者)的需求,当商品到货(状态变化)后,老板通知所有登记过的客户。

在前端中,DOM 事件监听、MutationObserver 等机制也体现了观察者模式的思想。

基本流程(发生了什么)

  1. 客户端创建被观察者(Subject)实例
  2. 客户端创建多个观察者(Observer)实例
  3. 观察者向被观察者发起订阅(subscribe/attach
  4. 被观察者在合适时机发布消息/状态变更(notify
  5. 所有观察者收到通知并执行各自的 update 逻辑

---

4. TypeScript 示例(接口约束 + Store 维护观察者列表)

下面示例中:

  • IObserver<T>:观察者必须实现的约束(必须有 update
  • Store<T>:被观察者,内部维护 observers 列表,支持 subscribe/unsubscribe/notify
// 观察者接口:成为观察者必须实现 update
export interface IObserver<T> {
  update(payload: T): void;
}

// 被观察者:维护观察者列表并负责通知
export class Store<T> {
  private observers = new Set<IObserver<T>>();

  subscribe(observer: IObserver<T>) {
    this.observers.add(observer);
  }

  unsubscribe(observer: IObserver<T>) {
    this.observers.delete(observer);
  }

  notify(payload: T) {
    for (const observer of this.observers) {
      observer.update(payload);
    }
  }
}

客户端使用示例:

import { IObserver, Store } from "./store";

type GoodsArrived = { sku: string; name: string; count: number };

class CustomerA implements IObserver<GoodsArrived> {
  update(payload: GoodsArrived) {
    console.log("CustomerA 收到通知:", payload);
  }
}

class CustomerB implements IObserver<GoodsArrived> {
  update(payload: GoodsArrived) {
    console.log("CustomerB 收到通知:", payload);
  }
}

const boss = new Store<GoodsArrived>();

const a = new CustomerA();
const b = new CustomerB();

boss.subscribe(a);
boss.subscribe(b);

// 老板“到货”并通知所有登记客户
boss.notify({ sku: "10086", name: "Apple", count: 10 });

要点:

  • 被观察者负责:维护列表 + 通知
  • 观察者负责:接收消息后的处理

5. 前端中的典型体现

5.1 DOM 事件监听

button.addEventListener("click", () => {
  console.log("点击事件触发");
});

这里按钮的点击事件发生时,会通知所有注册的监听器(观察者回调)。

5.2 MutationObserver

const observer = new MutationObserver((mutations) => {
  console.log("DOM 发生变化:", mutations);
});

observer.observe(document.body, {
  childList: true,
  subtree: true,
});

DOM 变化时,观察者回调会被触发。


6. 观察者模式 vs 发布订阅模式

二者常被混用,但并不相同:

  • 观察者模式:观察者与被观察者之间通常存在直接依赖关系(Subject 直接持有 Observer 列表并逐个通知)
  • 发布订阅模式(Pub/Sub):发布者与订阅者通常不直接相互引用,通过“事件总线/消息代理(Broker)”中转解耦(发布者只发布到 Broker,订阅者只从 Broker 订阅)

简单理解:观察者模式是“对象之间直接订阅与通知”,发布订阅模式是“通过中间件/消息中心解耦”。

使用社交账号登录

  • Loading...
  • Loading...
  • Loading...
  • Loading...
  • Loading...