创见博客
前端开发常见设计模式及实际应用
七崽爱吃小饼干2026/03/06阅读 1

前端常用设计模式主要分为创建型、结构型、行为型三类,都是日常写Vue/React/原生JS都会用到的核心模式。


一、创建型模式(控制对象创建)

1. 单例模式(Singleton)

核心:一个类只创建一个实例,全局共享访问。 前端应用:全局弹窗、全局状态管理、日志工具、请求封装实例。

javascript
// 全局弹窗单例(实际项目常用)
class GlobalModal {
  static instance = null;
  constructor() {
    if (GlobalModal.instance) return GlobalModal.instance;
    this.modal = document.createElement('div');
    this.modal.className = 'global-modal';
    document.body.appendChild(this.modal);
    GlobalModal.instance = this;
  }
  show(content) {
    this.modal.innerHTML = content;
    this.modal.style.display = 'block';
  }
}

// 使用:无论new多少次,都是同一个弹窗
const modal1 = new GlobalModal();
const modal2 = new GlobalModal();
console.log(modal1 === modal2); // true

实际业务:Element Plus 的 ElMessage、全局请求实例 axios.create 都是单例。


2. 工厂模式(Factory)

核心:封装对象创建逻辑,根据不同条件创建不同对象。 前端应用:表单组件工厂、权限控制、不同类型的弹窗/卡片渲染。

javascript
// 表单组件工厂:根据类型生成输入框/单选框/下拉框
class FormFactory {
  static create(type, options) {
    switch (type) {
      case 'input': return new Input(options);
      case 'radio': return new Radio(options);
      case 'select': return new Select(options);
      default: throw new Error('不支持的组件类型');
    }
  }
}

// 业务使用:一行代码创建不同组件
const usernameInput = FormFactory.create('input', { placeholder: '请输入用户名' });
const genderRadio = FormFactory.create('radio', { options: ['男', '女'] });

实际业务:低代码平台、动态表单、根据用户角色渲染不同页面模块。


二、结构型模式(组合对象/代码结构)

1. 适配器模式(Adapter)

核心:兼容两个不兼容的接口,不用修改原有代码。 前端应用:接口数据格式转换、第三方SDK兼容、新旧API适配。

javascript
// 场景:后端返回旧数据格式,前端需要新格式
// 旧接口数据
const oldApiData = { userName: "张三", userAge: 20 };
// 前端需要的格式
const newDataFormat = { name: "", age: 0 };

// 适配器:转换格式
function userAdapter(data) {
  return {
    name: data.userName,
    age: data.userAge
  };
}

// 使用
const adaptedData = userAdapter(oldApiData);
console.log(adaptedData); // { name: "张三", age: 20 }

实际业务:对接多个后端接口、兼容不同版本的UI库、微信/支付宝支付SDK统一适配。


2. 装饰器模式(Decorator)

核心:不修改原对象/函数,动态添加功能。 前端应用:函数增强、埋点统计、权限校验、日志打印。

javascript
// 原按钮点击函数
function submit() { console.log("提交表单"); }

// 装饰器:添加埋点功能
function withTrack(fn) {
  return function() {
    console.log("上报埋点:submit_click"); // 新增功能
    fn.apply(this, arguments); // 执行原逻辑
  }
}

// 装饰后的函数
const submitWithTrack = withTrack(submit);
submitWithTrack(); 
// 输出:上报埋点:submit_click → 提交表单

实际业务:Vue 自定义指令、React HOC、请求拦截/响应拦截、按钮防抖/节流封装。


3. 代理模式(Proxy)

核心:控制对原对象的访问,做拦截、校验、缓存。 前端应用:Vue3 响应式原理、图片懒加载、接口缓存、权限拦截。

javascript
// Vue3 响应式核心原理(简化版)
const target = { name: "前端开发" };
const proxy = new Proxy(target, {
  get(target, key) {
    console.log(`获取属性:${key}`);
    return Reflect.get(target, key);
  },
  set(target, key, value) {
    console.log(`设置属性:${key} = ${value}`);
    return Reflect.set(target, key, value);
  }
});

proxy.name; // 获取属性:name
proxy.name = "设计模式"; // 设置属性:name = 设计模式

实际业务:图片懒加载代理、敏感数据加密、接口请求缓存、防重复点击。


4. 组合模式(Composite)

核心:将对象组合成树形结构,统一处理单个对象和组合对象。 前端应用:树形菜单、文件目录、表单嵌套、组件树渲染。

javascript
// 树形菜单:叶子节点 + 父节点统一调用render()
class MenuItem {
  constructor(name) { this.name = name; }
  render() { console.log("渲染菜单项:", this.name); }
}

class MenuGroup {
  constructor(name) {
    this.name = name;
    this.children = [];
  }
  add(item) { this.children.push(item); }
  render() {
    console.log("渲染菜单组:", this.name);
    this.children.forEach(item => item.render());
  }
}

// 使用:组合成树形结构
const rootMenu = new MenuGroup("主菜单");
rootMenu.add(new MenuItem("首页"));
const subMenu = new MenuGroup("用户中心");
subMenu.add(new MenuItem("个人信息"));
rootMenu.add(subMenu);
rootMenu.render(); // 统一渲染整个树

实际业务:Vue/React 组件树、文件管理器、多级审批流。


三、行为型模式(对象间通信/逻辑)

1. 观察者模式(Observer)

核心:一对多依赖,一个对象变化,所有依赖者自动更新。 前端应用:事件监听、Vue/React 状态更新、消息订阅。

javascript
// 简易事件总线(Vue2 EventBus 原理)
class EventBus {
  constructor() { this.events = {}; }
  // 订阅事件
  on(eventName, callback) {
    if (!this.events[eventName]) this.events[eventName] = [];
    this.events[eventName].push(callback);
  }
  // 发布事件
  emit(eventName, data) {
    this.events[eventName]?.forEach(cb => cb(data));
  }
}

// 使用
const bus = new EventBus();
bus.on("login", (user) => console.log("用户登录:", user));
bus.emit("login", { name: "张三" });

实际业务:Vue 响应式、Redux 状态更新、WebSocket 消息推送、跨组件通信。


2. 发布-订阅模式(Publish-Subscribe)

和观察者区别:多了中间调度中心,解耦发布者和订阅者。 前端应用:全局消息通知、跨页面通信、模块化解耦。

日常开发中,EventBus 同时实现了发布-订阅模式,用法和上面一致。


3. 策略模式(Strategy)

核心:将算法/逻辑封装成策略,动态切换,避免大量 if-else。 前端应用:表单校验、支付方式切换、权限判断、打折计算。

javascript
// 表单校验策略:替换一堆if-else
const validateStrategies = {
  required: (val) => val ? true : "必填项不能为空",
  phone: (val) => /^1[3-9]\d{9}$/.test(val) ? true : "手机号格式错误",
  email: (val) => /^.+@.+\..+$/.test(val) ? true : "邮箱格式错误"
};

// 使用
console.log(validateStrategies.required("")); // 必填项不能为空
console.log(validateStrategies.phone("13800138000")); // true

实际业务:登录表单校验、电商优惠计算、不同支付渠道(微信/支付宝/银行卡)切换。


4. 迭代器模式(Iterator)

核心:顺序遍历集合,不用关心内部结构。 前端应用:数组遍历、Tree 数据遍历、自定义遍历逻辑。

javascript
// JS 原生已实现:for...of 就是迭代器
const arr = [1,2,3];
for (const item of arr) { console.log(item); }

// 自定义迭代器:遍历树形数据
function* treeIterator(tree) {
  for (const node of tree) {
    yield node;
    if (node.children) yield* treeIterator(node.children);
  }
}

实际业务:树形数据递归遍历、列表无限滚动、自定义数据遍历。


5. 命令模式(Command)

核心:将请求封装成命令对象,支持撤销/重做/队列执行。 前端应用:编辑器撤销重做、操作日志、任务队列。

javascript
// 命令对象:执行 + 撤销
class Command {
  constructor(execute, undo) {
    this.execute = execute;
    this.undo = undo;
  }
}

// 文本编辑命令
const addText = new Command(
  (str) => console.log("添加文字:", str),
  (str) => console.log("撤销文字:", str)
);

addText.execute("Hello"); // 添加文字:Hello
addText.undo("Hello"); // 撤销文字:Hello

实际业务:富文本编辑器、流程图操作撤销/重做、后台任务队列。


四、前端专属高频模式

1. 模块模式(Module)

核心:私有化变量,避免全局污染。 应用:原生JS模块化、IIFE、ES6 Module。

javascript
// ES6 模块天然支持私有化
const privateVar = "私有变量"; // 外部无法访问
export const publicFunc = () => console.log(privateVar);

2. 中介者模式(Mediator)

核心:对象间不直接通信,通过中介者统一调度。 应用:表单联动、多组件状态同步、聊天室。


五、快速选型指南

业务场景推荐设计模式
全局唯一工具/弹窗单例模式
动态创建组件/表单工厂模式
接口数据格式转换适配器模式
避免if-else/逻辑切换策略模式
组件通信/状态更新观察者/发布订阅
权限/缓存/拦截代理模式
树形结构/组件树组合模式
函数增强/埋点装饰器模式

总结

  1. 不用死记硬背:前端设计模式是解决实际问题的套路,记住「场景→模式」对应关系即可;
  2. 框架底层都在用:Vue3(Proxy)、React(HOC)、Redux(观察者)、EventBus(发布订阅);
  3. 核心价值:代码可维护、可扩展、解耦、少写if-else,提升开发效率和代码质量。
评论
0/100