1. 程式人生 > 程式設計 >javascript設計模式 – 簡單工廠模式原理與應用例項分析

javascript設計模式 – 簡單工廠模式原理與應用例項分析

本文例項講述了javascript設計模式 – 簡單工廠模式。分享給大家供大家參考,具體如下:

介紹:簡單工廠模式是最常用的一類建立型設計模式。其中簡單工廠模式並不屬於GoF23個經典設計模式,它通常被作為學習其他工廠模式的基礎。

定義:定義一個工廠類,它可以根據引數的不同返回不同的例項,被建立的例項通常都具有相同的父類,因為在簡單工廠模式中建立例項的方法是靜態方法,因此簡單工廠模式又被稱為靜態工廠方法模式,它屬於類建立型模式。

場景:我們需要寫一個dialog工具類,在專案初期我們只需要考慮一個簡單的彈窗實現,專案持續迭代,會衍生出各種型別的彈窗,帶關閉按鈕的,帶確認按鈕的…..

我見到最多的做法是根據一個type值來判斷當前需要彈什麼型別的視窗,這樣的設計我之前沒覺得有問題,但是看了前面介紹的設計原則,我們也來分析下這麼做的缺點:

1. 存在多個if…else…程式碼塊,程式碼冗長,閱讀困難,維護困難,測試困難,影響系統性能。
2. dialog類職責過重,負責初始化所有彈窗例項,違反了單一職責原則,不利於重用和維護。
3. 當需要新增彈窗型別是,必須修改原始碼,違反了開關原則。
4. 不同種類彈窗基礎樣式相同,會導致存在大量重複程式碼。
5. 各類彈窗的建立和使用都是在各個業務邏輯中,如果我想修改建立方式必須修改所有業務程式碼,違反了開關原則

示例:

var Dialog = (function(){
  var createNotice = function(){
    return '<div>notice</div>';
  }
  var createToast = function(){
    return '<div>toast</div>';
  }
  var createWarnin = function(){
 return '<div>warnin</div>';
  }
  var Dialog = function(){
 this.element = '';
 this.name = '';
 this.show = function(){
   console.log(this.name + ' is show -> ' + this.element);
 };
  }
 
  return {
 factory: function(arg){
   var _dialog;
   if(arg === 'notice'){
     _dialog = new Dialog();
     _dialog.element = createNotice();
     _dialog.name = 'notice';
     }else if(arg === 'toast'){
     _dialog = new Dialog();
     _dialog.element = createToast();
     _dialog.name = 'toast';
   }else if(arg === 'warnin'){
     _dialog = new Dialog();
     _dialog.element = createWarnin();
     _dialog.name = 'warnin';
   }
   return _dialog;
 }
  }
})();
 
var notice = Dialog.factory('notice');
var toast = Dialog.factory('toast');
var warnin = Dialog.factory('warnin');
toast.show(); //toast is show -> <div>toast</div>
notice.show(); //notice is show -> <div>notice</div>
warnin.show(); //warnin is show -> <div>warnin</div>

以上的解決方案是自己理解著寫的,對照著java的示例寫了一個,實現的方式有很多種,你可以用原型鏈,用繼承來實現都可以。我們這裡主要討論下為什麼要這麼寫。

之前我們列出了5個缺點:我們主要解決了2,4和5,將共有的方法屬性抽取出來寫在父類上,減少了重複程式碼,將每種情況特有的程式碼抽取出來,解決了不符合單一職責原則的問題。

重要的是將所有彈窗的建立集中在工廠類中,當有修改時,只需要修改工廠類即可,不會影響業務程式碼。

這裡我們思考一下:1.如何去掉那些if…else…? 2.當我要新增一個error型別的彈窗時如何滿足開關原則?

我自己試了一下:

var Dialog = function(){
  this.element = '';
  this.name = '';
  this.show = function(){
 console.log(this.name + ' is show -> ' + this.element);
  };
}
 
Dialog.createNotice = function(){ return '<div>notice</div>'; };
Dialog.createToast = function(){ return '<div>toast</div>'; };
Dialog.createWarnin = function(){ return '<div>warnin</div>'; };
Dialog.factory = function(arg){ 
  var _dialog = new Dialog();
  _dialog.element = Dialog[arg]();
  _dialog.name = arg;
  return _dialog;
};
 
var notice = Dialog.factory('createNotice');
var toast = Dialog.factory('createToast');
var warnin = Dialog.factory('createWarnin');
notice.show(); //createNotice is show -> <div>notice</div>
warnin.show(); //createWarnin is show -> <div>warnin</div>
toast.show(); //createToast is show -> <div>toast</div>

這樣當我做新增時,只需要要新增一條配置即可,不用去對公告內容做修改。滿足了開關原則的對擴充套件支援對修改關閉。

簡單工廠模式總結:

優點:
* 簡單工廠模式實現了物件建立和使用的分離

缺點:
* 工廠模式集中了所有產品的建立邏輯,職責過重,一旦出現問題會影響到整個系統

適用場景:
* 適用於建立的物件比較少,由於建立的物件較少,不會造成工廠方法中的業務邏輯太過複雜
* 客戶端只知道傳入工廠類的引數,對於如何建立物件並不關心

感興趣的朋友可以使用線上HTML/CSS/JavaScript程式碼執行工具:http://tools.jb51.net/code/HtmlJsRun測試上述程式碼執行效果。

更多關於JavaScript相關內容感興趣的讀者可檢視本站專題:《javascript面向物件入門教程》、《JavaScript錯誤與除錯技巧總結》、《JavaScript資料結構與演算法技巧總結》、《JavaScript遍歷演算法與技巧總結》及《JavaScript數學運算用法總結》

希望本文所述對大家JavaScript程式設計有所幫助。