单例模式
单例模式确保一个类只有一个实例,并提供一个全局访问点。在前端开发中常用于全局状态管理、缓存、日志记录等场景。
核心思想
单例模式通过限制类的实例化次数为一次,确保在整个应用程序中只有一个实例存在。这有助于节省内存资源,同时提供统一的访问入口。
JavaScript实现
单例模式实现
// ES6实现单例模式 class Singleton { constructor() { if (!Singleton.instance) { this.data = []; this.config = {}; Singleton.instance = this; } return Singleton.instance; } addData(item) { this.data.push(item); } getData() { return this.data; } setConfig(key, value) { this.config[key] = value; } getConfig(key) { return this.config[key]; } } // 使用示例 const instance1 = new Singleton(); const instance2 = new Singleton(); console.log(instance1 === instance2); // true,两个变量引用同一个实例 instance1.addData('item1'); console.log(instance2.getData()); // ['item1'],共享数据 // 更简洁的实现方式(闭包) const createSingleton = () => { let instance; const init = () => { // 私有变量和方法 let privateData = []; // 公有方法 return { add: (item) => privateData.push(item), getAll: () => [...privateData], clear: () => privateData = [] }; }; return { getInstance: () => { if (!instance) { instance = init(); } return instance; } }; }; const singleton = createSingleton(); const app1 = singleton.getInstance(); const app2 = singleton.getInstance(); console.log(app1 === app2); // true
优点
- 确保全局只有一个实例,节省内存
- 提供全局访问点,便于管理共享资源
- 避免重复创建相同对象
- 便于实现延迟初始化
缺点
- 可能导致全局状态污染
- 难以进行单元测试
- 违反单一职责原则
- 可能隐藏类之间的依赖关系
使用场景
- 全局配置管理
- 缓存系统
- 日志记录器
- 状态管理(如Redux Store)
- 对话框/模态框管理
- 数据库连接池
工厂模式
工厂模式提供了一种创建对象的方式,而无需指定具体的类。它将对象的创建逻辑封装起来,使代码更加灵活和可维护。
核心思想
工厂模式定义一个创建对象的接口,但让子类决定实例化哪个类。工厂方法让类的实例化延迟到子类,增加了代码的灵活性和可扩展性。
JavaScript实现
工厂模式实现
// 简单工厂模式 class Button { constructor(text) { this.text = text; } render() { return `<button>${this.text}</button>`; } } class Input { constructor(placeholder) { this.placeholder = placeholder; } render() { return `<input placeholder="${this.placeholder}" />`; } } class FormFactory { static createElement(type, options) { switch (type) { case 'button': return new Button(options.text); case 'input': return new Input(options.placeholder); default: throw new Error('Unknown element type'); } } } // 使用示例 const button = FormFactory.createElement('button', { text: '点击我' }); const input = FormFactory.createElement('input', { placeholder: '请输入...' }); console.log(button.render()); // "<button>点击我</button>" console.log(input.render()); // "<input placeholder='请输入...' />" // 工厂方法模式 class Dialog { createButton() { throw new Error('必须实现 createButton 方法'); } render() { const button = this.createButton(); return `Dialog with ${button.render()}`; } } class WindowsDialog extends Dialog { createButton() { return new WindowsButton(); } } class <