前陣子準備期末考試,挺累也挺忙的,實在閒不得空來更新文章,今天和你們說說javascript
中的設計模式。javascript
首先呢,咱們須要知道的是:模式
是一種可複用的解決方案,而反模式
呢就是針對某個問題的不良解決方案。java
setTimeout
和setInterval
傳遞字符串,而不是函數,這會觸發eval()
的內部使用。Object
類的原型js
,嵌入在HTML文件中的js
代碼是沒法包含在外部單元測試工具中的。document.write
,若是在頁面加載完成後執行docume.write
,它會重寫咱們所在的頁面,可使用document.creatElement
代替的話就儘可能不用docume.write
。建立型設計模式專一於處理對象建立機制,以適合給定狀況的方式來建立對象。屬於這個類別的屬性包括:設計模式
Constructor構造器、Factory工廠、Abstract抽象、Prototype原型、Singleton單例和Builder生成器
結構型模式與對象組合有關,一般能夠用於找出在不一樣對象之間創建關係的簡單方法。
屬於這個類別的模式包括:函數
Decorator裝飾者、Facade外觀、Flyweight享元、Adapter適配器和Proxy代理
行爲模式專一於改善或簡化系統中不一樣對象之間的通訊。工具
行爲模式包括:單元測試
Iterator迭代器、Mediator中介者、Observer觀察者和Visitor訪問者
爲了解決多個相似對象聲明的問題,咱們可使用一種叫作 工廠模式
的方法,這種方法 就是爲了解決實例化對象
產生大量重複的問題。測試
<script type="text/javascript"> function createObject(name,age,profession){//集中實例化的函數 var obj = new Object(); obj.name = name; obj.age = age; obj.profession = profession; obj.move = function () { return this.name + ' at ' + this.age + ' engaged in ' + this.profession; }; return obj; } var test1 = createObject('trigkit4',22,'programmer');//第一個實例 var test2 = createObject('mike',25,'engineer');//第二個實例 alert(test1.move()); alert(test2.move()); </script>
工廠模式分爲簡單工廠、抽象工廠和智能工廠,工廠模式不顯示地要求使用一個構造函數。ui
簡單工廠模式:使用一個類(一般爲單體)來生成實例。
複雜工廠模式:使用子類來決定一個成員變量應該是哪一個具體的類的實例。this
主要好處就是能夠消除對象間的耦合,經過使用工程方法而不是new關鍵字。將全部實例化的代碼集中在一個位置防止代碼重複。
大多數類最好使用new關鍵字和構造函數,可讓代碼更加簡單易讀。而沒必要去查看工廠方法來知道。
工廠模式解決了重複實例化的問題 ,但還有一個問題,那就是識別問題,由於根本沒法 搞清楚他們究竟是哪一個對象的實例。prototype
alert(typeof test1); //Object alert(test1 instanceof Object); //true
Factory
模式主要在如下場景使用:
ECMAScript
中能夠採用構造函數(構造方法)可用來建立特定的對象。 該模式正好能夠解決以上的工廠模式沒法識別對象實例的問題。
<script type="text/javascript"> function Car(model,year,miles){//構造函數模式 this.model = model; this.year = year; this.miles = miles; this.run = function () { return this.model + " has done " + this.miles + "miles"; } } var Benz = new Car('Benz',2014,20000); var BMW = new Car("BMW",2013,12000); alert(Benz instanceof Car); //很清晰的識別他從屬於 Car,true console.log(Benz.run()); console.log(BMW.run()); </script>
使用構造函數的方法 ,即解決了重複實例化的問題 ,又解決了對象識別的問題,該模式與工廠模式的不一樣之處在於:
1.構造函數方法沒有顯示的建立對象 (new Object()); 2.直接將屬性和方法賦值給 this 對象; 3.沒有 renturn 語句。
構造函數的方法有一些規範:
1.函數名和實例化構造名相同且大寫, (PS:非強制,但這麼寫有助於區分構造函數和 普通函數); 2.經過構造函數建立對象,必須使用 new 運算符。
既然經過構造函數能夠建立對象,那麼這個對象是哪裏來的, new Object()
在什麼地方執行了?執行的過程以下:
1.當使用了構造函數,而且 new 構造函數(),那麼就後臺執行了 new Object(); 2.將構造函數的做用域給新對象 ,(即 new Object()建立出的對象),而函數體內的 this 就 表明 new Object()出來的對象。 3.執行構造函數內的代碼; 4.返回新對象(後臺直接返回)。
js
中有一個名爲prototype
的屬性。調用js
構造器建立一個對象後,新對象就會具備構造器原型的全部屬性。經過這種方式,能夠建立多個Car
對象,並訪問相同的原型。
<script type="text/javascript"> function Car(model,year,miles) { this.model = model; this.year = year; this.miles = miles; } Car.prototype.run = function () { return this.model + " has done " + this.miles + " miles "; }; var Benz = new Car('S350',2010,20000); var Ford = new Car('Ford',2012,12000); console.log(Benz.run());//"S350 has done 20000 miles " console.log(Ford.run()); </script>
如今run()
的單一實例就可以在全部Car對象之間共享。