设计模式在 TypeScript 中的实现

设计模式在 TypeScript 中的实现

欢迎继续本专栏的第三十八篇文章。在前几期中,我们已逐步深化了对 TypeScript 性能优化的理解,包括避免 any 类型的策略、类型推断的优化技巧,以及在大型项目中的性能考虑。这些实践帮助我们构建了更高效和可维护的代码基础。今天,我们将转向设计模式这一经典主题,探讨如何在 TypeScript 中实现它们。设计模式是解决常见软件设计问题的可复用解决方案,我们将通过示例实现单例、工厂和观察者模式,并利用 TypeScript 的类型系统增强这些模式的可靠性和表达力。设计模式并非一成不变的规则,而是指导原则,在 TypeScript 中,它们能与静态类型结合,提供更强的编译时保证。我们将从设计模式的基础概念入手,逐步深入到每个模式的实现细节,并分析 TypeScript 类型系统如何提升模式的安全性和灵活性。通过由浅入深的讲解、丰富示例和实际场景分析,我们旨在帮助您掌握这些模式的核心,并在项目中应用它们,构建更模块化和可扩展的软件架构。内容将从设计模式的基本原理展开到高级应用,确保您能从简单实现过渡到类型增强的优化,并获得深刻的实践洞见。

理解设计模式在 TypeScript 中的定位

设计模式是软件工程中经过验证的解决方案,用于解决重复出现的特定问题。它们源于 GoF(Gang of Four)的经典著作《设计模式》,分为创建型、结构型和行为型三类。在 TypeScript 中,设计模式定位于桥接面向对象原则与类型安全的结合:TS 的静态类型系统能强化模式的约束,确保实现符合意图,同时减少运行时错误。例如,单例模式保证唯一实例,TS 类型能防止误用;工厂模式抽象创建,类型系统确保返回类型一致;观察者模式处理事件,接口定义订阅合同。

设计模式的定位在于提升代码的可复用性、可维护性和扩展性。在动态的 JavaScript 环境中,模式帮助管理复杂性;TS 通过类型注解和接口,让模式更 robust。例如,利用泛型增强工厂的灵活性,或用类型守卫确保观察者的参数安全。根据软件工程实践,使用设计模式的 TS 项目,代码重构成本可降低 15-25%,尤其在大型应用如企业系统或前端框架中。相比纯 JavaScript,TS 的类型系统让模式从“约定”转为“强制”,减少隐蔽 bug。

为什么选择单例、工厂和观察者?它们代表创建型(工厂、单例)和行为型(观察者)的典型,能展示 TS 类型增强的多样性。我们将从每个模式的基础开始,逐步引入 TS 优化,确保您能理解模式如何从简单实现演变为类型安全的结构,同时避免模式滥用导致的复杂性。

设计模式在 TypeScript 中的应用历史与 OOP 语言同步,但 TS 的类型特性让它们更现代化,在框架如 Angular 或 NestJS 中广泛实现依赖注入和事件处理。这让模式成为架构设计的工具,在实际开发中帮助管理状态和交互。

设计模式的基础:创建型、结构型和行为型的概述

在深入具体模式前,理解设计模式的分类有助于把握其作用。创建型模式关注对象创建,如单例确保唯一、工厂抽象实例化;结构型模式组织类和对象,如适配器转换接口;行为型模式定义通信,如观察者处理通知。

在 TypeScript 中,基础模式实现类似于 JS,但类型系统添加约束:接口定义合同,泛型提供灵活,类型守卫确保安全。这让模式不只是结构,还带有编译时验证。例如,创建型模式用类型确保返回对象符合形状。

基础概述为具体模式铺路:我们将重点创建型(单顿、工厂)和行为型(观察者),因为它们常见,且 TS 类型增强显著。

单例模式:确保唯一实例

单例模式是一种创建型模式,确保类只有一个实例,并提供全局访问点。它适合管理共享资源,如配置或数据库连接。

单例模式的基础实现

在 TypeScript 中,基本单例用私有构造函数和静态方法:

classSingleton{privatestaticinstance:Singleton|null=null;privateconstructor(){// 私有,防止直接 new}publicstaticgetInstance():Singleton{if(!Singleton.instance){Singleton.instance=newSingleton();}returnSingleton.instance;}publicsomeMethod():void{console.log("Singleton method called");}}

使用:

consts1=Singleton.getInstance();consts2=Singleton.getInstance();console.log(s1===s2);// trues1.someMethod();

基础:静态 instance 存储唯一对象,getInstance 控制访问。

单例模式的深入实现与优化

懒加载:如上,首次调用创建。

线程安全:在 JS 单线程中无需锁,但 Node 多进程可用。

初始化数据:

classConfigSingleton{privatestaticinstance:ConfigSingleton|null=null;privateconfig:{[key:string]:string}={};privateconstructor(configData:{[key:string]:string}){this.config=configData;}publicstaticgetInstance(configData?:{[key:string]:string}):ConfigSingleton{if(!ConfigSingleton.instance){if(!configData)thrownewError("Config data required for initialization");ConfigSingleton.instance=newConfigSingleton(configData);}returnConfigSingleton.instance;}publicget(key:string):string|undefined{returnthis.config[key];}}

深入:优化添加重置测试,但生产慎用。

单例深入让它适合全局状态,但避免滥用导致耦合。

利用 TypeScript 类型系统增强单例模式

TS 类型增强单例:私有构造确保类型安全,静态方法返回精确类型。

类型增强的基本应用

上示例中,getInstance 返回 Singleton 类型,确保方法可用。

防止误用:

私有构造编译时防 new Singleton()。

类型增强的深入技巧

泛型单例:

classGenericSingleton<T>{privatestaticinstances:Map<any,any>=newMap();privateconstructor(privatedata:T){}publicstaticgetInstance<U>(key:any,data:U):GenericSingleton<U>{if(!GenericSingleton.instances.has(key)){GenericSingleton.instances.set(key,newGenericSingleton(data));}returnGenericSingleton.instances.get(key);}publicgetData():T{returnthis.data;}}

多键单例,泛型 T 确保 data 类型。

深入:结合接口。

interfaceILogger{log(message:string):void;}classLoggerSingletonimplementsILogger{// 单例实现log(message:string):void{console.log(message);}}constlogger=LoggerSingleton.getInstance();logger.log("Message");// 类型 ILogger

类型增强深入让单例安全,TS 接口定义合同。

工厂模式:抽象对象创建

工厂模式是创建型模式,提供接口创建对象,而不暴露逻辑。适合当创建复杂或有变体时。

工厂模式的基础实现

简单工厂:

classProductA{operation():string{return"ProductA operation";}}classProductB{operation():string{return"ProductB operation";}}classSimpleFactory{staticcreateProduct(type:string):ProductA|ProductB|null{if(type==="A")returnnewProductA();if(type==="B")returnnewProductB();returnnull;}}

使用:

constprod=SimpleFactory.createProduct("A");console.log(prod?.operation());

基础:工厂方法集中创建逻辑。

工厂模式的深入实现

抽象工厂:接口定义工厂,具体类实现。

interfaceIProduct{operation():string;}classConcreteProduct1implementsIProduct{operation():string{return"ConcreteProduct1";}}classConcreteProduct2implementsIProduct{operation():string{return"ConcreteProduct2";}}interfaceIFactory{createProduct():IProduct;}classFactory1implementsIFactory{createProduct():IProduct{returnnewConcreteProduct1();}}classFactory2implementsIFactory{createProduct():IProduct{returnnewConcreteProduct2();}}functionclientCode(factory:IFactory){constproduct=factory.createProduct();console.log(product.operation());}clientCode(newFactory1());// "ConcreteProduct1"

深入:抽象工厂支持家族产品,易切换。

工厂深入让创建解耦,适合 DI。

利用 TypeScript 类型系统增强工厂模式

TS 类型增强工厂:泛型确保返回类型,接口定义合同。

类型增强的基本应用

泛型工厂:

classFactory{staticcreate<T>(ctor:new()=>T):T{returnnewctor();}}classMyClass{}constinstance=Factory.create(MyClass);// 类型 MyClass

基本:泛型 T 推断自 ctor。

类型增强的深入技巧

类型安全的抽象工厂:

interfaceIButton{render():void;}interfaceICheckbox{render():void;}interfaceIGUIFactory{createButton():IButton;createCheckbox():ICheckbox;}classWindowsButtonimplementsIButton{render():void{console.log("Windows Button");}}classWindowsCheckboximplementsICheckbox{render():void{console.log("Windows Checkbox");}}classWindowsFactoryimplementsIGUIFactory{createButton():IButton{returnnewWindowsButton();}createCheckbox():ICheckbox{returnnewWindowsCheckbox();}}classMacButtonimplementsIButton{render():void{console.log("Mac Button");}}classMacCheckboximplementsICheckbox{render():void{console.log("Mac Checkbox");}}classMacFactoryimplementsIGUIFactory{createButton():IButton{returnnewMacButton();}createCheckbox():ICheckbox{returnnewMacCheckbox();}}functionapplication(factory:IGUIFactory){constbutton=factory.createButton();button.render();constcheckbox=factory.createCheckbox();checkbox.render();}application(newWindowsFactory());// Windows UIapplication(newMacFactory());// Mac UI

接口 IGUIFactory 确保工厂返回正确类型,类型系统检查实现。

深入技巧:泛型工厂参数化。

typeConstructor<T>=new(...args:any[])=>T;functioncreateInstance<T>(ctor:Constructor<T>,...args:any[]):T{returnnewctor(...args);}classUser{constructor(publicname:string){}}constuser=createInstance(User,"Alice");// 类型 User

类型增强深入让工厂安全,TS 泛型和接口防止错创建。

观察者模式:实现事件通知

观察者模式是行为型模式,定义一对多依赖,当主体变化,所有观察者通知。

观察者模式的基础实现

简单:

classSubject{privateobservers:(()=>void)[]=[];attach(observer:()=>void):void{this.observers.push(observer);}detach(observer:()=>void):void{this.observers=this.observers.filter(obs=>obs!==observer);}notify():void{this.observers.forEach(obs=>obs());}}classObserver{update():void{console.log("Updated");}}constsubject=newSubject();constobs1=newObserver();constobs2=newObserver();subject.attach(()=>obs1.update());subject.attach(()=>obs2.update());subject.notify();// "Updated" twice

基础:Subject 管理观察者,notify 调用 update。

观察者模式的深入实现

发布订阅变体:

interfaceIObserver{update(data:any):void;}classPublisher{privatesubscribers:{[event:string]:IObserver[]}={};subscribe(event:string,observer:IObserver):void{if(!this.subscribers[event])this.subscribers[event]=[];this.subscribers[event].push(observer);}unsubscribe(event:string,observer:IObserver):void{this.subscribers[event]=this.subscribers[event].filter(obs=>obs!==observer);}publish(event:string,data:any):void{this.subscribers[event]?.forEach(obs=>obs.update(data));}}classSubscriberimplementsIObserver{update(data:any):void{console.log("Received:",data);}}constpublisher=newPublisher();constsub1=newSubscriber();publisher.subscribe("event1",sub1);publisher.publish("event1","data");// "Received: data"

深入:事件键分订阅,支持多事件。

观察者深入让模式适合 UI 事件或状态变化。

利用 TypeScript 类型系统增强观察者模式

TS 类型增强观察者:接口定义 update 签名,泛型指定 data 类型。

类型增强的基本应用

类型化 update:

interfaceIObserver<T>{update(data:T):void;}classSubject<T>{privateobservers:IObserver<T>[]=[];attach(observer:IObserver<T>):void{this.observers.push(observer);}notify(data:T):void{this.observers.forEach(obs=>obs.update(data));}}classObserverimplementsIObserver<string>{update(data:string):void{console.log(data);}}constsubject=newSubject<string>();constobs=newObserver();subject.attach(obs);subject.notify("message");// OK// subject.notify(123); // 错误

基本:泛型 T 确保 data 类型一致。

类型增强的深入技巧

事件类型映射:

typeEvents={click:MouseEvent;keypress:KeyboardEvent;};classEventEmitter{privatelisteners:{[KinkeyofEvents]?:((event:Events[K])=>void)[]}={};on<KinkeyofEvents>(event:K,listener:(ev:Events[K])=>void):void{if(!this.listeners[event])this.listeners[event]=[];this.listeners[event]!.push(listener);}emit<KinkeyofEvents>(event:K,data:Events[K]):void{this.listeners[event]?.forEach(listener=>listener(data));}}constemitter=newEventEmitter();emitter.on("click",ev=>console.log(ev.clientX));// ev MouseEvent// emitter.on("click", ev => ev.key); // 错误

keyof + mapped 类型确保事件数据匹配。

深入技巧:TS 类型让观察者类型安全,防止错数据。

实际应用:设计模式在项目中的实践

单例在配置管理。

工厂在 DI 容器。

观察者在 Redux 状态订阅。

案例:游戏引擎,用单例资源管理,工厂实体创建,观察者事件系统。

实践提升架构。

高级设计模式:与 TS 结合的扩展

策略模式用类型守卫。

代理模式用装饰器。

高级扩展模式。

风险与最佳实践

风险:

  • 模式滥用复杂。
  • 无类型模式运行错。
  • 继承过多 fragile。

实践:

  • 简单优先模式。
  • 类型化所有接口。
  • 测试模式行为。
  • 文档模式意图。

确保有效。

案例研究:真实项目

Angular 服务用工厂。

RxJS 观察者。

NestJS 单例模块。

改善 25%。

结语:设计模式,TS 架构的指南针

通过本篇文章的详尽探讨,您已掌握单例、工厂和观察者实现的细节,以及 TS 类型增强。这些模式将助您设计优雅代码。实践:实现单例。下一期 React 与 TS,敬请期待。若疑问,欢迎交流。我们继续。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/1220996.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

2026年1月线切割机床厂家推荐排行榜,中走丝/快走丝/电火花线切割机床,穿孔机,精密高效加工设备源头厂商精选

2026年1月线切割机床厂家推荐排行榜:中走丝/快走丝/电火花线切割机床与穿孔机精密高效加工设备源头厂商精选 随着制造业向高精度、高效率、智能化方向持续演进,特种加工技术在现代工业体系中的地位日益凸显。线切割机…

C盘爆红怎么办!几招彻底清理电脑C盘空间

真实用户求救&#xff1a;C盘红了&#xff0c;我慌了&#xff01; “昨天开黑突然卡死&#xff0c;一看C盘只剩200MB&#xff01;不得不考虑清理电脑c盘空间&#xff01;c盘爆红了可以删除哪些文件&#xff1f;怕删错系统崩了...求大神指点怎么清除电脑c盘的空间才安全&#x…

研发需求排期实战指南:工具选型、流程搭建与效能提升

在研发项目节奏日益加快、需求来源日趋多元的今天&#xff0c;混乱的需求排期往往会导致研发资源浪费、项目延期交付、团队精力内耗等一系列问题。然而&#xff0c;需求的繁杂并非最棘手的——棘手的是无法在业务价值、研发成本与时间周期之间找到平衡。研发需求排期工具的核心…

聊聊AI智能客服

一、关于AI智能客服新闻事件分析报告解读 现象概述:AI智能客服在企业服务中广泛应用,具有效率高、成本低等优势,中国智能客服市场规模不断增长,前景良好。但它存在不能解决个性化问题、交流缺乏情感、转人工流程复杂等问题,易引发用户抵触。同时,有人在探索AI客服的配置及…

破解协作低效难题:中小企业流程数字化工具及核心策略

在数字化转型浪潮下&#xff0c;中小企业面临着流程繁琐、协作低效、数据孤岛、成本高企等诸多痛点。相较于大型企业&#xff0c;中小企业资源有限、人员精简、业务灵活&#xff0c;传统的纸质流程或零散的办公软件早已无法满足高效运营的需求。然而&#xff0c;转型的难点并非…

测试用例执行进度实时同步工具指南:从流程打通到效率提效的全链路落地

在软件研发全生命周期中&#xff0c;测试环节是保障产品质量的核心防线&#xff0c;而测试用例执行的效率与透明度&#xff0c;直接决定了研发迭代的节奏与产品交付的质量。当测试团队跨岗位协作、多版本并行测试时&#xff0c;信息滞后、进度不透明、同步不及时等问题&#xf…

【无人机追踪】基于资源福利任务分配算法的无人机集群任务分配算法,完成目标攻击任务的基础上,无人机的资源利用率最大化 + 资源损耗的公平性最优附Matlab代码2

✅作者简介&#xff1a;热爱科研的Matlab仿真开发者&#xff0c;擅长数据处理、建模仿真、程序设计、完整代码获取、论文复现及科研仿真。&#x1f34e; 往期回顾关注个人主页&#xff1a;Matlab科研工作室&#x1f447; 关注我领取海量matlab电子书和数学建模资料 &#x1f34…

2026年铝板厂家推荐排行榜:幕墙铝板、氟碳铝板、木纹铝板、蜂窝铝板、异型铝板等全品类实力厂家深度解析与选购指南

2026年铝板厂家推荐排行榜:幕墙铝板、氟碳铝板、木纹铝板、蜂窝铝板、异型铝板等全品类实力厂家深度解析与选购指南 随着建筑美学与功能需求的不断演进,铝板材料以其轻质高强、耐候性强、造型丰富、绿色环保等综合优…

RAG 不是万能解,这些场景你一开始就不该用

RAG并非万能,默认滥用反致系统复杂、效果难测。它仅解决“信息获取”,不提升模型能力。最适合四类场景:动态知识更新、需答案溯源、长尾问题密集、需求尚不明确。慎用于强推理、隐性经验、高实时性及高确定性要求场…

零基础想转行网络安全?这3个方向门槛低、就业快

【收藏】网络安全转行避坑指南&#xff1a;零基础无需报班&#xff0c;3个方向半年拿offer&#xff0c;薪资比IT高37% 网络安全人才缺口大&#xff0c;零基础转行无需报班。可考虑三个方向&#xff1a;运维工程师(网络防护&#xff0c;3个月就业&#xff0c;起薪1.2-1.5万)&am…

运维人别内耗!转行网安,薪资翻倍+职业逆袭指南

【必收藏】运维转网络安全&#xff1a;3步实现薪资翻倍&#xff0c;告别35岁危机&#xff01; 运维人员转行网络安全具有天然优势&#xff0c;因为运维经验&#xff08;系统管理、网络配置、日志分析等&#xff09;正是网安工作的基础。运维人员对安全风险的亲身经历也让他们更…

2026网络安全这趟车_你还敢上吗?

网络安全真相大揭秘&#xff1a;2026年入坑指南&#xff0c;收藏级内容&#xff0c;小白程序员必读 网络安全行业现状严峻&#xff1a;求职竞争激烈&#xff0c;企业需要的是真正理解攻防逻辑的人才而非工具使用者&#xff1b;安全部门常被视为成本中心&#xff0c;在公司预算…

2026年,还能继续入网络安全行业吗?那些行业不敢说的秘密

收藏&#xff01;2026年网安行业生存指南&#xff1a;不推荐入行&#xff1f;先了解真相再决定 文章揭示2026年网络安全行业面临就业难、收入不稳定、企业重视度低等挑战。企业需要能发现漏洞、写工具、理解攻防逻辑的人才&#xff0c;而非只会使用工具的"工具人"。…

普通本科转行网络安全5年,现在月薪2W+,劝你想清楚!

【收藏级】网络安全自学指南&#xff1a;零基础到实战的完整路径&#xff0c;少走弯路必备 这是一位有五年网络安全经验的从业者分享的入门指南。作者强调行业缺的是能解决问题的人&#xff0c;而非只会背理论的人。文章从零基础到进阶&#xff0c;推荐了多个学习资源&#xf…

IP6163至为芯支持MPPT功能的太阳能电池板充电DC-DC芯片

英集芯IP6163是一款应用于太阳能电池板供电的锂电池/磷酸铁锂电池充电方案芯片。集成MCU的高效光伏降压MPPT DC-DC控制器。内置专用MPPT硬件与动态算法&#xff0c;峰值效率达99.9%&#xff0c;可快速锁定太阳能电池板的最大功率点。支持6-40V宽电压输入&#xff0c;兼容最多72…

轨道小车无线控制系统设计与实现

在汽车制造、仓储物流、冶金化工等场景中&#xff0c;轨道小车是物料转运的“动脉”&#xff0c;其控制精度与运行效率直接影响生产节拍与成本。然而&#xff0c;传统有线控制模式面临布线复杂、维护成本高、移动受限等痛点&#xff0c;拖链电缆频繁弯折导致断裂、信号衰减&…

【图像加密】基于DCT变换的图像加密与解密附matlab代码

✅作者简介&#xff1a;热爱科研的Matlab仿真开发者&#xff0c;擅长数据处理、建模仿真、程序设计、完整代码获取、论文复现及科研仿真。 &#x1f34e; 往期回顾关注个人主页&#xff1a;Matlab科研工作室 &#x1f447; 关注我领取海量matlab电子书和数学建模资料 &#…

2026年想给Facebook广告账户充值,到底该找谁?这里有一份详细的避坑指南

对于在2026年寻求出海增长的企业而言,Meta(Facebook)依然是不可绕过的核心流量阵地。然而,随着Meta广告政策在2026年的进一步收紧——特别是新增的“AI生成内容强制标注”规定、东南亚市场的“本土主体优先”规则以…

144. 二叉树的前序遍历-day11

题目:144. 二叉树的前序遍历 题目链接:https://leetcode.cn/problems/binary-tree-preorder-traversal/description/ 思路:1. 确定终止条件 2. 确定执行一次递归的函数过程 3. 确定参数及返回值 代码:点击查看代码…

2026年 电机厂家推荐排行榜:直驱电机/线性电机/无框电机/力矩电机/高频电机,核心技术与高效能解决方案深度解析

2026年电机厂家推荐排行榜:直驱电机/线性电机/无框电机/力矩电机/高频电机,核心技术与高效能解决方案深度解析 随着工业自动化、精密制造和高端装备领域的飞速发展,对运动控制核心部件——电机的性能要求达到了前所…