摘要:在面向對象的語言中,比如,等,單例模式通常是定義類時將構造函數設為,保證對象不能在外部被出來,同時給類定義一個靜態的方法,用來獲取或者創建這個唯一的實例。
萬事開頭難,作為正經歷菜鳥賽季的前端player,已經忘記第一次告訴自己要寫一些東西出來是多久以的事情了。。。如果,你也和我一樣,那就像我一樣,從現在開始,從看到這篇文章開始,打開電腦,敲下你的第一篇文章(或者任何形式的文字)吧。
首先,respect一下:以下文章內容全部來自最近在看的一本書《javascript設計模式與開發實踐》,作者曾探。感謝作者的辛苦付出,以下內容算是個人的一個讀書筆記,如果有理解有誤或不合適的內容,歡迎隨時聯系更改或刪除。
其次,歡迎各路大神diss。
最后,接下來正式開始我的flow。
一、什么是設計模式
相信任何一個從事和代碼相關工作的人都或多或少地聽說過“設計模式”這個名詞,每個人也都有自己的理解。從我個人來看,設計模式就是“套路”,知道了這個套路的話,你就多了一些處理問題的技能(或者是更優雅地解決);那么,如果不知道這個套路也并不能說明什么,只是你還沒總結或者你正在使用卻不自知而已。即使是真的不知道,也沒關系,就從這篇文章開始吧。
設計模式的思想來源于建筑行業,建筑學的研究人員花了長達20年的時間總結了在建筑中為解決同樣的問題而設計的不同的建筑結構,從中找到一些高質量的相似的通用結構,稱之為“模式”,軟件工程大神們受到啟發,進而總結了23種常用的軟件開發設計模式,錄入到《設計模式:可復用面向對象軟件的基礎》
設計模式的定義是:在面向對象軟件設計過程中針對特定問題的簡潔而優雅的解決方案(并不必須是面向對象)。通俗來說,設計模式就是給我們軟件開發過程中經常用的一些套路起了一個名字,就變成了一個看起來很高大上的東西。
建筑會因為不同的風格去對一些相同的結構做一些不一樣的設計,對軟件來說也一樣,不同的語言,設計模式的實現也是不一樣的。google的某一位大神曾經在文章中指出23種設計模式有16種已經在lisp中默認實現了。比如,命令模式,在java中需要一個命令類,一個接受者類,一個調用者類,并把命令對象在接受者類中四處傳遞。但在lisp或javascript這種將函數作為一等公民的語言中,函數本身就可以在對象中互相傳遞,因此,命令模式在這兩種語言中就成為了一種隱性模式。
智者說,凡是都有度(別問我是哪個智者)。對于鼓吹設計模式和貶低設計模式的,我只能說,你牛你有理。個人認為應該沒有放之四海而皆準的東西(貌似是個悖論,尷尬)。如果有,那就有吧,反正不是設計模式。為什么說設計模式簡潔而優雅的解決方案,是因為從軟件開發的角度來看,健壯和易擴展是非常非常重要的衡量指標,而設計模式恰恰幫助我們更好地解決了這個問題。但為什么說“度”呢,因為設計模式也并不適合用在任何開發的過程中。如果在一個簡單的小項目中,明明一個函數就可以完成的功能,非要為了炫技或其他什么原因,增加額外的許多代碼實現一個模式,項目代碼增加許多,自然增加了bug的幾率。另外,明明是一次使用的東西,偏偏要做過度的設計去用模式做擴展設計,這自然也是沒有必要的。
二、設計模式之單例模式
單例模式應該是設計模式中最簡單的一個模式,在許多書中都是作為第一個來講。單例,顧名思義,保證一個類只有一個實例,并在項目代碼中可以全局被訪問。
在面向對象的語言中,比如,c++、java等,單例模式通常是定義類時將構造函數設為private,保證對象不能在外部被new出來,同時給類定義一個靜態的方法,用來獲取或者創建這個唯一的實例。javascript同樣可以模仿這個過程來實現單例,代碼如下:
var Singleton = function (name) { this.name = name; this.instance = null; } Singleton.getInstance = function(name) { if (!this.instance) { this.instance = new Singleton(name); } return this.instance; }
很顯然,我們在代碼中需要用到Singleton的時候,只需要Singleton.getInstance("PGOne")即可獲得唯一的實例。但是卻有一些缺陷:當我們new Singleton("Gai")的時候,仍可以new出實例,另外,Singleton做了一些和自己無關的事情,于是乎就有了另一種實現。
var Singleton = function (name) { this.name = name; this.instance = null; } var ProxySingleton = (function () { var instance; return function (name) { if (!instance) { instance = new Singleton(name); } return instance; } })();
在這種實現中,我們可以通過new ProxySingleton("PGOne")獲取Singleton的實例,單例控制就分離到了代理類中,保證了Singleton的純潔。甚至可以把Singleton使用閉包封裝成私有變量,徹底阻止直接的new調用。
上面這些是在JavaScript中模仿靜態語言c++或java中單例模式的實現,但是,在JavaScript中,看起來似乎有些奇怪和多余。因為,JavaScript作為一種無類(class-freee)語言,生搬過來的單例模式并沒有太多意義。在JavaScript中,常見對象非常簡單,如果需要一個單例,我們只需要聲明一個字面量的對象,作為全局變量就可以了,何必聲明一個構造函數,再去new出來呢?雖然全局變量不是單例模式,但是在JavaScript中,我們卻常常把全局變量當做單例模式來用,因為它確實能完成單例模式的功能。但是全局變量最大的問題就是污染全局空間,以至于一直以來,濫用全局變量都被視為糟糕的代碼。為了盡可能減少全局變量的影響,在JavaScript中,命名空間和閉包封裝私有變量成了慣用的手段。那么在JavaScript中,單例到底應該是什么樣子呢?JavaScript終極單例如下:
var Singleton = function (fn) { var result; return function () { return result || (result = fn.apply(this, arguments)); } } var createSingleDialog = function() { var div = document.createElement("div"); div.innerHTML = "我是彈窗"; div.style.display = "none"; document.body.appendChild("div"); return div; } // 使用 var getDialog = Singleton(createSingleDialog); document.getElementById("btn").onclick = function () { var dialog = getDialog(); dialog.style.display = "block"; }
在上面代碼中,Singleton是一個通用的代理管理器,可以通過傳入不同的功能函數進而返回一個單例獲取器。在上面代碼中,是獲取一個彈窗的單例,我們同樣可以通過傳入一個導航欄生成函數,來獲取一個導航欄的單例。另外,上面代碼中,單例只在需要的時候才會被創建,這也是單例模式所要求的,然而,通過全局對象和閉包實現的單例,確實在開始就創建了實例。
需要說明的是,由于javascript的應用場景主要在瀏覽器,通過dom操作也同樣可以做到單例,所以new這樣的單例看起來使用場景并不大,但是,上面的一小段代碼遠不止單例那么簡答。在實際的開發中,我們經常會遇到這樣的問題,在異步獲取數據之后或是彈窗出來的時候,需要給一部分的dom元素綁定事件。比如說,有一個負責數據展示和操作的彈窗,每次彈窗顯示的時候都需要將新的數據綁定到彈窗的dom元素上,這時就會遇到dom重復綁定事件的問題,上面代碼就可以完美解決這個問題。
var bindEvent = getSingle(function () { document.getElement("btn").onClick = function(){ alert("new data"); } return true; }); var showDialog = function () { console.log("顯示彈窗"); bindEvent(); } showDialog(); showDialog();
第一次寫東西,感覺想要把一個東西寫清楚還真是一件復雜的事情。
許久不見朋友突然的一個約飯,幫朋友搬一天的家,諸多借口,又差點掐死了這篇內容。還好,我今天不困。復制粘貼一番,勉強寫出來一點。
設計模式,未完待續。。。。
番外:
to be real很酷,但請不要為了real而real。人人都向往自由,但世界卻不能沒了規則。客套,請不要假裝不懂。
----中國有嘻哈觀感,我站萬磁王!
文章版權歸作者所有,未經允許請勿轉載,若此文章存在違規行為,您可以聯系管理員刪除。
轉載請注明本文地址:http://specialneedsforspecialkids.com/yun/85224.html
摘要:但是,不合理地濫用閉包,也會造成很多性能問題,從而使項目維護成本增加。 前言 相信很多小伙伴在工作或者面試過程中都遇到過這個問題,作為經典的前端面試題之一,它高頻地出現在我們的求職生涯中。所以,了解和掌握它也就變得十分必要了 讀完這篇文章,你或許就會知道: 閉包是什么,它是怎么形成的 為什么要使用閉包 閉包會造成哪些問題 如果文章中有出現紕漏、錯誤之處,還請看到的小伙伴多多指教,先...
摘要:對深度學習模型而言,水就是海量的數據。就拿機器識別物體這樣的任務來說,通過數百萬副圖片的訓練,深度學習模型甚至可以超過人的肉眼的識別能力,這確實是人工智能在感知類問題上重要的里程碑。關于深度學習,還有一個有趣的現象。 說到人工智能和機器人,上點兒歲數的碼農們可能對封面這張圖有點印象。不明就里的朋友,可以回去補習一下《編輯部的故事》。我是個二手的人工智能表演藝術家:從博士畢業開始,就在MSRA...
閱讀 2189·2021-11-15 11:38
閱讀 1151·2021-09-06 15:02
閱讀 3380·2021-08-27 13:12
閱讀 1353·2019-08-30 14:20
閱讀 2389·2019-08-29 15:08
閱讀 636·2019-08-29 14:08
閱讀 1723·2019-08-29 13:43
閱讀 1464·2019-08-26 12:11