開發人員都應該瞭解的 7 種 JavaScript 設計模式

来源:https://www.cnblogs.com/coderhf/archive/2020/07/01/13219852.html
-Advertisement-
Play Games

開發人員將 JavaScript 設計模式作為解決問題的模板是很合適的,但並不是說這些模式可以代替開發人員的工作。 通過設計模式,我們可以將許多開發人員的經驗結合起來,以優化過的方式來構造代碼,從而解決我們所面對的問題。設計模式還提供了用於描述問題解決方案的通用辭彙表,而不是去枯燥地描述代碼的語法和 ...


開發人員將 JavaScript 設計模式作為解決問題的模板是很合適的,但並不是說這些模式可以代替開發人員的工作。

通過設計模式,我們可以將許多開發人員的經驗結合起來,以優化過的方式來構造代碼,從而解決我們所面對的問題。設計模式還提供了用於描述問題解決方案的通用辭彙表,而不是去枯燥地描述代碼的語法和語義。

JavaScript 設計模式可幫助開發人員編寫出井井有條、美觀且結構合理的代碼。儘管設計模式很容易重用,但它們並不是要取代開發人員的工作;它們是開發人員的支持與輔助,提供了與特定應用程式無關的通用解決方案,從而儘量避免那些可能導致 Web 應用程式的開發工作出現重大問題的小漏洞。

與臨時方案相比,它們消除了不必要的重覆,從而縮減了代碼庫的整體大小,並讓我們的代碼更加健壯。

在本文中,我將探討 7 種最出色和最受歡迎的 JavaScript 設計模式,這些模式主要歸為以下三類:創作設計模式、結構設計模式和行為設計模式。

1、構造函數設計模式

這是一種特殊的方法,用於在分配記憶體後初始化新創建的對象。由於 JavaScript 一般來說是面向對象的,所以它打交道最多的就是對象。於是我打算深入研究對象構造函數。在 JavaScript 中創建新對象有三種方法可用。

以下創建構造函數設計模式的一種方法。

 // 創建一個新的空對象
 var newObject = {};
 // 創建一個新的空對象
 var newObject = Object.create(Object.prototype);
 var newObject = newObject();

 

要訪問函數的屬性,你需要初始化對象。

 const object = new ConstructorObject();

 

上面的 new 關鍵字告訴 JavaScript,一個 constructorObject 應該充當一個構造函數。這個設計模式並不支持繼承。更多細節可以參考這裡

2、原型模式

原型模式是基於原型繼承的。在這種模式中,被創建的對象充當其他對象的原型。實際上,原型(prototype)是被創建的每個對象構造函數的藍圖。

示例:

 var myCar= {
 name:"Ford Escort",
 brake:function(){
 console.log("Stop! I am applying brakes");
 }
 Panic : function (){
 console.log ( "wait. how do you stop thuis thing?")
 }
 }
 // 使用 object create 實個新的例化一 car
 var yourCar= object.create(myCar);
 // 現在它就是另一個的原型了
 console.log (yourCar.name);]

 

3、模塊設計模式

模塊(module)設計模式對原型模式做了一些改進。模塊模式設置了不同類型的修飾符(私有和公共)。你可以創建相似的函數或屬性而不會發生衝突。我們還可以靈活地公開重命名函數。這個設計模式的一個缺陷是無法覆蓋(override)外部環境中創建的函數。

示例:

 function AnimalContainter () {
 const container = [];
 function addAnimal (name) {
 container.push(name);
 }
 function getAllAnimals() {
 return container;
 }
 function removeAnimal(name) {
 const index = container.indexOf(name);
 if(index < 1) {
 throw new Error('Animal not found in container');
 }
 container.splice(index, 1)
 }
 return {
 add: addAnimal,
 get: getAllAnimals,
 remove: removeAnimal
 }
 }
 const container = AnimalContainter();
 container.add('Hen');
 container.add('Goat');
 container.add('Sheep');
 console.log(container.get()) //Array(3) ["Hen", "Goat", "Sheep"]
 container.remove('Sheep')
 console.log(container.get()); //Array(2) ["Hen", "Goat"]

 

4、單例模式

在僅需要創建一個實例的情況下(例如一個資料庫連接),這個模式是必需的。在這個模式中,只能在關閉連接時創建一個實例,或者在打開新實例之前必須關閉已有的實例。此模式也稱為嚴格模式,它的一個缺點是測試時的體驗很差,因為它隱藏的依賴項對象很難挑出來進行測試。

示例:

 function DatabaseConnection () {
 let databaseInstance = null;
 // 追蹤特定時間創建實例的數量
 let count = 0;
 function init() {
 console.log(`Opening database #${count + 1}`);
 // 現在執行操作
 }
 function createIntance() {
 if(databaseInstance == null) {
 databaseInstance = init();
 }
 return databaseInstance;
 }
 function closeIntance() {
 console.log('closing database');
 databaseInstance = null;
 }
 return {
 open: createIntance,
 close: closeIntance
 }
 }
 const database = DatabseConnection();
 database.open(); //Open database #1
 database.open(); //Open database #1
 database.open(); //Open database #1
 database.close(); //close database

 

5、工廠模式

這個模式的創新之處在於,它不需要構造函數就能創建對象。它提供了用於創建對象的通用介面,我們可以在其中指定要創建的工廠(factory)對象的類型。這樣一來,我們只需指定對象,然後工廠會實例化並返回這個對象供我們使用。當對象組件設置起來很複雜,並且我們希望根據所處的環境輕鬆地創建不同的對象實例時,使用工廠模式就是很明智的選擇。在處理許多共用相同屬性的小型對象,以及創建一些需要解耦的對象時也可以使用工廠模式。

示例:

 // Dealer A
 DealerA = {};
 DealerA.title = function title() {
 return "Dealer A";
 };
 DealerA.pay = function pay(amount) {
 console.log(
 `set up configuration using username: ${this.username} and password: ${
 this.password
 }`
 );
 return `Payment for service ${amount} is successful using ${this.title()}`;
 };
 //Dealer B
 DealerB = {};
 DealerB.title = function title() {
 return "Dealer B";
 };
 DealerB.pay = function pay(amount) {
 console.log(
 `set up configuration using username: ${this.username}
 and password: ${this.password}`
 );
 return `Payment for service ${amount} is successful using ${this.title()}`;
 };
 //@param {*} DealerOption
 //@param {*} config
 function DealerFactory(DealerOption, config = {}) {
 const dealer = Object.create(dealerOption);
 Object.assign(dealer, config);
 return dealer;
 }
 const dealerFactory = DealerFactory(DealerA, {
 username: "user",
 password: "pass"
 });
 console.log(dealerFactory.title());
 console.log(dealerFactory.pay(12));
 const dealerFactory2 = DealerFactory(DealerB, {
 username: "user2",
 password: "pass2"
 });
 console.log(dealerFactory2.title());
 console.log(dealerFactory2.pay(50));

 

6、觀察者模式

觀察者(observer)設計模式在許多對象同時與其他對象集通信的場景中用起來很方便。在觀察者模式中不會在狀態之間發生不必要的事件 push 和 pull;相比之下,所涉及的模塊僅會修改數據的當前狀態。

示例:

 function Observer() {
 this.observerContainer = [];
 }
 Observer.prototype.subscribe = function (element) {
 this.observerContainer.push(element);
 }
 // 下麵是從 container 中移除一個元素
 Observer.prototype.unsubscribe = function (element) {
 const elementIndex = this.observerContainer.indexOf(element);
 if (elementIndex &gt; -1) {
 this.observerContainer.splice(elementIndex, 1);
 }
 }
 /**
 * we notify elements added to the container by calling
 * each subscribed components added to our container
 */
 Observer.prototype.notifyAll = function (element) {
 this.observerContainer.forEach(function (observerElement) {
 observerElement(element);
 });
 }

 

7、命令模式 最後介紹的是命令(command)模式。命令設計模式將方法調用、操作或請求封裝到單個對象中,以便我們可以自行傳遞方法調用。命令設計模式讓我們可以從任何正在執行的命令中發出命令,並將責任委托給與之前不同的對象。這些命令以 run() 和 execute() 格式顯示。

 (function(){
 var carManager = {
 // 請求的信息
 requestInfo: function( model, id ){
 return "The information for " + model + " with ID " + id + " is foo bar";
 },
 // 現在購買這個 car
 buyVehicle: function( model, id ){
 return "You have successfully purchased Item " + id + ", a " + model;
 },
 // 現在 arrange viewing
 arrangeViewing: function( model, id ){
 return "You have successfully booked a viewing of " + model + " ( " + id + " ) ";
 }
 };
 })();

 

小結

對於 JavaScript 開發人員來說,使用設計模式的好處很多。設計模式的一些主要優點包括提升項目的可維護性,還能減少開發周期中不必要的工作。JavaScript 設計模式可以為複雜的問題提供解決方案,提升開發速度並提高生產率。但並不能說這些設計模式就可以讓開發人員偷懶了。

如果你覺得這篇文章不錯,請別忘記點個關註哦~

您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • 前言: 最近在整理自己的技術棧,收集了一些自己認為比較重要的知識點分享給大家。 Runloop 1. iOS中觸摸事件傳遞和響應原理 2. 為什麼只有主線程的runloop是開啟的 3. 為什麼只在主線程刷新UI 4. PerformSelector和runloop的關係 5.GCD 在Runloo ...
  • 一、數組遍歷和其他 1.合併數組 數組.concat(數組1,數組2,數組3,...) 可以用來合併多個數組 //合併多個數組concat var arr = ["zhangsan","lisi","wangwu"]; var arr1 = ["zhaoli","liqi"]; var arr2 = ...
  • 頁面強行註入jQuery這個腳手架,然後可以用jQuery幹些事情了。 ...
  • 課程開始,今天學習了html的基本標簽: div + span: div和span兩個是雙標簽,html中有雙標簽和單標簽,下文中有單標簽介紹 ,雙標簽成雙成對出現例如: <div> <span></span> </div> 有<div>必定要有</div>這就是雙標簽的特性。 div和span沒有 ...
  • 觀察自然界中樹的分叉,一根主幹生長出兩個側乾,每個側乾又長出兩個側乾,以此類推,便生長出疏密有致的結構。這樣的生長結構,使用遞歸演算法可以模擬出來。 例如,分叉的側乾按45°的偏轉角度進行生長的遞歸示意圖如圖1所示。 圖1 生成樹的遞歸示意圖 按照樹分叉生長側乾的遞歸思想,編寫如下的HTML代碼。 < ...
  • 1 <!DOCTYPE html> 2 <html> 3 <head> 4 <meta charset="utf-8"> 5 <title>JavaScript中的運算符</title> 6 </head> 7 <body> 8 <script type="text/javascript"> 9 / ...
  • 1 <!DOCTYPE html> 2 <html> 3 <head> 4 <meta charset="utf-8"> 5 <title>JavaScript簡介</title> 6 </head> 7 <body> 8 <script type="text/javascript"> 9 wind ...
  • 想學習 TypeScript 的小伙伴看過來,本文將帶你一步步學習 TypeScript 入門相關的十四個知識點,詳細的內容大綱請看下圖: 一、TypeScript 是什麼 TypeScript 是一種由微軟開發的自由和開源的編程語言。它是 JavaScript 的一個超集,而且本質上向這個語言添加 ...
一周排行
    -Advertisement-
    Play Games
  • .Net8.0 Blazor Hybird 桌面端 (WPF/Winform) 實測可以完整運行在 win7sp1/win10/win11. 如果用其他工具打包,還可以運行在mac/linux下, 傳送門BlazorHybrid 發佈為無依賴包方式 安裝 WebView2Runtime 1.57 M ...
  • 目錄前言PostgreSql安裝測試額外Nuget安裝Person.cs模擬運行Navicate連postgresql解決方案Garnet為什麼要選擇Garnet而不是RedisRedis不再開源Windows版的Redis是由微軟維護的Windows Redis版本老舊,後續可能不再更新Garne ...
  • C#TMS系統代碼-聯表報表學習 領導被裁了之後很快就有人上任了,幾乎是無縫銜接,很難讓我不想到這早就決定好了。我的職責沒有任何變化。感受下來這個系統封裝程度很高,我只要會調用方法就行。這個系統交付之後不會有太多問題,更多應該是做小需求,有大的開發任務應該也是第二期的事,嗯?怎麼感覺我變成運維了?而 ...
  • 我在隨筆《EAV模型(實體-屬性-值)的設計和低代碼的處理方案(1)》中介紹了一些基本的EAV模型設計知識和基於Winform場景下低代碼(或者說無代碼)的一些實現思路,在本篇隨筆中,我們來分析一下這種針對通用業務,且只需定義就能構建業務模塊存儲和界面的解決方案,其中的數據查詢處理的操作。 ...
  • 對某個遠程伺服器啟用和設置NTP服務(Windows系統) 打開註冊表 HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\W32Time\TimeProviders\NtpServer 將 Enabled 的值設置為 1,這將啟用NTP伺服器功 ...
  • title: Django信號與擴展:深入理解與實踐 date: 2024/5/15 22:40:52 updated: 2024/5/15 22:40:52 categories: 後端開發 tags: Django 信號 松耦合 觀察者 擴展 安全 性能 第一部分:Django信號基礎 Djan ...
  • 使用xadmin2遇到的問題&解決 環境配置: 使用的模塊版本: 關聯的包 Django 3.2.15 mysqlclient 2.2.4 xadmin 2.0.1 django-crispy-forms >= 1.6.0 django-import-export >= 0.5.1 django-r ...
  • 今天我打算整點兒不一樣的內容,通過之前學習的TransformerMap和LazyMap鏈,想搞點不一樣的,所以我關註了另外一條鏈DefaultedMap鏈,主要調用鏈為: 調用鏈詳細描述: ObjectInputStream.readObject() DefaultedMap.readObject ...
  • 後端應用級開發者該如何擁抱 AI GC?就是在這樣的一個大的浪潮下,我們的傳統的應用級開發者。我們該如何選擇職業或者是如何去快速轉型,跟上這樣的一個行業的一個浪潮? 0 AI金字塔模型 越往上它的整個難度就是職業機會也好,或者說是整個的這個運作也好,它的難度會越大,然後越往下機會就會越多,所以這是一 ...
  • @Autowired是Spring框架提供的註解,@Resource是Java EE 5規範提供的註解。 @Autowired預設按照類型自動裝配,而@Resource預設按照名稱自動裝配。 @Autowired支持@Qualifier註解來指定裝配哪一個具有相同類型的bean,而@Resourc... ...