1、介紹javascript
每當我聽到有人討論設計模式時,我聽到最多的概念好像就是「工廠模式」,他就像是背單詞時候的「abandon」,它易於理解且常常用到,因此我也將它做爲學習「設計模式」的第一步。前端
咱們都知道,工廠模式是爲了建立對象而存在的(主要是聽到的太多了~)。對象是一個系統的基石,咱們編寫的功能均可以抽象成由一個個對象組合而成,請求是由一個個XmlHttpRequest對象執行的、頁面由一個個DOM節點對象堆砌而成等等。咱們在前端框架之中每每會對請求做一層層的封裝(好比咱們會在JQuery.ajax、axios之上再封裝一層),那咱們在生成這些對象的時候,會發現他們都有着類似之處,就像是由工廠生產出來的一個個產品,那咱們封裝的過程其實就和「工廠模式」很相近了。java
工廠模式屬於「建立型模式」的一種,與之相關的有:簡單工廠模式、工廠模式和抽象工廠模式。ios
簡單工廠模式能夠理解爲「一家工廠根據不一樣的模具來生產產品」的模式,以下舉例:git
// 工廠 class SimpleRequestFactory { constructor() {} createRequest(type) { let req = null; switch (type) { case 'get': req = new GetRequest(); // GetRequest爲get請求的模具 break; case 'post': req = new PostRequest(); // PostRequest爲post請求的模具 break; } return req; } } // 工廠生產處get請求的產品 const getRequestInstance = SimpleRequestFactory.createRequest('get'); getRequestInstance.setUrl('https://xxx'); // 設置get請求的url getRequestInstance.setParams({id: 'xxx'}); // 設置get請求的參數 getRequestInstance.request(); // 工廠生產處post請求的產品 const postRequestInstance = SimpleRequestFactory.createRequest('post'); postRequestInstance.setUrl('https://xxx'); // 設置post請求的url postRequestInstance.setParams({id: 'xxx'}); // 設置post請求的參數 getRequestInstance.request();
以上就是簡單工廠模式運行模式,利用這種方式,咱們就能夠根據不一樣請求的須要,來不斷生產request請求對象,咱們並不須要關心request的實例對象是怎麼生成的,咱們只須要獲得它、使用它便可。github
因此「簡單工廠模式」的特色就是:ajax
由上面的代碼咱們也能看出,簡單工廠模式是具備三大要素的:axios
工廠模式是在簡單工廠模式之上作了優化處理以後造成一種模式,咱們先看有關於工廠模式的代碼設計模式
class RequestFactory { constructor() {} createRequest() { // 我只表明每種RequestFactory都要實現createRequest方法 // 而我不生產任何產品 } } // get請求的工廠 class GetRequestFactory extends RequestFactory { constructor() {} createRequest() { return new GetRequest(); } } // post請求的工廠 class PostRequestFactory extends RequestFactory { constructor() {} createRequest() { return new PostRequest(); } } // put請求的工廠 class PutRequestFactory extends RequestFactory { constructor() {} createRequest() { return new PutRequest(); } } // 生產get請求的產品 const getRequestIns = GetRequestFactory.createRequest(); getRequestIns.setUrl('https://xxx'); // 設置get請求的url getRequestIns.setParams({id: 'xxx'}); // 設置get請求的參數 getRequestIns.request(); // 生產post請求的產品 const postRequestIns = PostRequestFactory.createRequest(); postRequestIns.setUrl('https://xxx'); // 設置get請求的url postRequestIns.setParams({id: 'xxx'}); // 設置get請求的參數 postRequestIns.request(); // 生產put請求的產品 const putRequestIns = PutRequestFactory.createRequest(); putRequestIns.setUrl('https://xxx'); // 設置get請求的url putRequestIns.setParams({id: 'xxx'}); // 設置get請求的參數 putRequestIns.request();
由上面的代碼能夠看出,咱們把每一種請求的生產工廠都獨立出來了,看似沒有簡單工廠模式方便,可是咱們能夠在生活之中找到例子輔助理解。前端框架
好比咱們A公司是一家生產飲品的公司,咱們最開始有一條生產線專門生產礦泉水,咱們叫「XX山泉」,後來咱們發現礦泉水作的不錯,咱們想多作一些產品,如「XX AD鈣奶」和「XX 純牛奶」,那咱們應該怎麼作呢?這時咱們可能根據生活中看到的例子,能夠想到,咱們只要照搬A公司的基礎部門(如行政),再成立幾家公司,分別生產「XX AD鈣奶」和「XX 純牛奶」便可。那咱們爲何不在A公司的基礎上不斷擴充生產線呢?由於一旦生產線愈來愈多,管理就愈來愈複雜,咱們須要不斷地折騰A公司,還不如複製一個抽象公司,而後專事專作。
上面的例子就是爲了幫助咱們理解「簡單工廠模式」和「工廠模式」的區別的,那咱們何時用哪一種模式呢?個人理解就是:
其實上面說的也關乎到設計模式中的一個原則——「開閉原則」。
再回到「工廠模式」之上,咱們能夠看到工廠模式的特色就是:
「工廠模式」包含四大要素:
此時確定有朋友想到了一個問題:「現實中咱們也並非全部的工廠都只生產一類產品,牛奶工廠能夠生產純牛奶、酸奶等等」,這就是咱們提到的抽象工廠模式了。示例代碼以下
// 抽象工廠 class RequestFactory { constructor() {} createRequest() { // 我只表明每種RequestFactory都要實現createRequest方法 // 而我不生產任何產品 } } /** 看這 start **/ // 抽象的get請求 class GetRequest{ constructor() {} request() {} } // 簡單的get請求(不須要帶參數的get請求) class SimpleGetRequest extends GetRequest{ constructor() {} request() {} } // 普通的get請求 class NormalGetRequest extends GetRequest{ constructor() {} request() {} } // 抽象的post請求 class PostRequest{ constructor() {} request() {} } // 簡單的post請求(不須要帶參數的post請求) class SimplePostRequest{ constructor() {} request() {} } // 普通的post請求 class NormalPostRequest extends PostRequest{ constructor() {} request() {} } /** 看這 end **/ // get請求的工廠 class GetRequestFactory extends RequestFactory { constructor() {} createSimpleRequest() { return new SimpleGetRequest(); } createNormalRequest() { return new NormalGetRequest(); } } // post請求的工廠 class PostRequestFactory extends RequestFactory { constructor() {} createSimpleRequest() { return new SimplePostRequest(); } createNormalRequest() { return new NormalPostRequest(); } } // 生產get請求的產品 const simpleGetRequestIns = GetRequestFactory.createSimpleRequest(); simpleGetRequestIns.setUrl('https://xxx'); // 設置get請求的url simpleGetRequestIns.setParams({id: 'xxx'}); // 設置get請求的參數 simpleGetRequestIns.request(); const normalGetRequestIns = GetRequestFactory.createNormalRequest(); normalGetRequestIns.setUrl('https://xxx'); // 設置get請求的url normalGetRequestIns.setParams({id: 'xxx'}); // 設置get請求的參數 normalGetRequestIns.request(); // 生產post請求的產品 const simplePostRequestIns = PostRequestFactory.createSimpleRequest(); simplePostRequestIns.setUrl('https://xxx'); // 設置get請求的url simplePostRequestIns.setParams({id: 'xxx'}); // 設置get請求的參數 simplePostRequestIns.request(); const normalPostRequestIns = PostRequestFactory.createNormalRequest(); normalPostRequestIns.setUrl('https://xxx'); // 設置get請求的url normalPostRequestIns.setParams({id: 'xxx'}); // 設置get請求的參數 normalPostRequestIns.request();
經過上面的代碼,咱們能夠看到,抽象工廠模式之於工廠模式的不一樣就是在工廠模式的基礎上,對產品也進行了一層抽象,從而實現了一個實體工廠也能生產多個產品的功能。
「抽象工廠模式」的好處就是:
「抽象工廠模式」有五大要素:
大話設計模式 - 程傑