JS常見構造模式實例對比分析
本文實例分析了JS常見構造模式。分享給大家供大家參考,具體如下:
1.工廠模式
沒有解決對象識別的問題。因為函數(shù)內(nèi)部使用了new Object來創(chuàng)建對象
function Factory(name,age) { var o=new Object(); o.name=name; o.age=age; o.what=what;//用函數(shù)引用的方式消除重復創(chuàng)建相同函數(shù)的弊端,節(jié)省資源.函數(shù)引用可以修改this的指向,函數(shù)調(diào)用不可以! return o; } what=funciton() { alert(this.name+this.age); } var o=Factory("12",12); o.what();//what中的this指向o對象
這時候的constructor是Object,同時所有通過工廠模式返回的對象都是Object類型,所以instanceof
操作符沒有意義
console.log(o.constructor); //打印function Object() { [native code] } console.log(o instanceof Object); //而且這時候所有的對象都是Object類型的
2.構造函數(shù)模式
function Person(name,age) { this.name=name; this.age=age; this.sayName=function(){ alert(this.name);}//相當于this.sayName=new Function("alert(this.name)") } var p1=new Person("xx",12); var p2=new Person("yy",13); alert(p1.sayName==p2.sayName)//內(nèi)存地址不一樣!返回false
構造函數(shù)相比工廠模式的優(yōu)點在于能夠正確的返回對象的類型,instanceof
返回正確的結果。缺點在于如果向上面那樣,那么在每一個對象上面都要有一個sayName方法,而且這些sayName方法不是同一個Function實例,因為ECMAScript中函數(shù)是對象,因此每定義一個函數(shù),也就是實例化了一個對象!
對上面的方法進行優(yōu)化:
function Person(name,age) { this.name=name; this.age=age; this.sayName=sayName;//函數(shù)引用的方法,共享了同一個sayName,p1,p2的內(nèi)存地址一樣,p1.sayName==p2.sayName返回true } function sayName() { alert(this.name); }
缺點:全局函數(shù)sayName只能被某個對象調(diào)用p1.sayName
,讓全局函數(shù)名不副實;如果對象要定義很多方法,那么就要定義很多的全局函數(shù),所以自定義的引用類型沒有封裝性可言
3.原型模式
(1)無法通過構造函數(shù)參數(shù)向原型屬性動態(tài)傳值,后果就是:沒有個性,改變原型屬性的值,所有的實例都會受到干擾!
(2)當原型屬性的是引用類型的時候,如果在一個對象實例上修改屬性,將會影響所有實例!
總之一句話:牽一發(fā)而動全身(包括屬性和引用類型的值)是原型模式的特點。但是相比于構造函數(shù)類型,原型類型滿足
person1.sayName===person2.sayName//兩者的引用是一樣的
4.構造函數(shù)原型模式
用構造函數(shù)定義個性,用原型模式定義共性
function Person(name,age) { this.name=name; this.age=age; this.friends=['liangklfang','qinliang']; } //用原型定義共性 Person.prototype={ constructor:Person, sayName:function() { console.log(this.name); } } var person1=new Person('liangklfang',"12"); var person2=new Person('liangklf',"14"); console.log(person1.sayName===person2.sayName); //共性是函數(shù),打印true console.log(person1.friends===person2.friends); //friends是個性,打印false
也可以對構造函數(shù)原型模式進行優(yōu)化,就是常說的動態(tài)原型模式
function Book(title,page) { this.title=title; this.page=page; if(typeof Book.isLock=="undefined") //第一次的時候,Book.isLock是undefined,給原型綁定函數(shù),以后就不需要了,他相比于構造函數(shù)原型模式的優(yōu)點在于把所有的邏輯全部封裝到構造函數(shù)里面! { alert("Enter!"); Book.prototype.what=function() { alert(this.title+this.pages); } Book.isLock=true; } } //下面的兩次調(diào)用alert("Enter!")只會調(diào)用因此i,因為第一次已經(jīng)通過Book.isLock設置為true了!相當于靜態(tài)方法!; var b1=new Book("me",12); b1.what(); var b2=new Book("he",13); b2.what();
也可以在this
中直接檢測,而不用給函數(shù)對象一個屬性
function Book(title,page) { this.title=title; this.page=page; if(typeof this.sayName!='function') //第二次構造對象的時候會在原型中查找到sayName! { Book.prototype.sayName=function() { console.log(this.title); } } }
5.寄生構造函數(shù)模式
除了使用new
操作符以外,和工廠設計模式是一模一樣的!可以在特殊的情況下為對象創(chuàng)建構造函數(shù),例如想用構造函數(shù)方式創(chuàng)建一個具有額外方法的特殊數(shù)組,因為不能直接修改Array的構造函數(shù),因此可以用這個模式!
function SpecialArray() { var value=new Array(); value.push.apply(value,arguments); value.toPipedString=function() { return this.join("|"); } return value; }
總之,寄生構造函數(shù)的特點就是:有點像java中的裝飾模式!把原來的對象進行裝飾,同時返回裝飾后的對象!這里就是把Array對象進行了裝飾!添加了toPipe的String
方法。缺點就是不能依賴instanceof
操作符確定對象類型了,因為和不再包裝類里面創(chuàng)建的對象是一模一樣的!
6. 穩(wěn)妥構造函數(shù)模式
特點:沒有公共屬性,而且其方法也不引用this的對象,instanceof
失效。和寄生構造函數(shù)的不同在于不使用new
來構造函數(shù),同時實例方法不引用this
。實際是閉包
function Person(name,age,job) { var o=new Object(); o.sayName=funciton(){alert(name)}//這里實例方法沒有引用this,除了sayName不會有方法訪問傳入到構造函數(shù)中的原始數(shù)據(jù)! return o; } var friend=Person("xx",12,"teacher"); friend.name="female";//即使可以為這個對象修改了屬性name friend.sayName();//不會被修改,依然彈出xx。不是female。但是,如果把上面的修改成:o.sayName=function(){alert(this.name)}//那么就會彈出female,也就是friend.name被修改成功了,如果沒有this,那么name的值一直引用的是原來的參數(shù)值!
感興趣的朋友還可以使用在線HTML/CSS/JavaScript代碼運行工具:http://tools.jb51.net/code/HtmlJsRun測試運行上述js代碼。
更多關于JavaScript相關內(nèi)容感興趣的讀者可查看本站專題:《javascript面向對象入門教程》、《JavaScript錯誤與調(diào)試技巧總結》、《JavaScript數(shù)據(jù)結構與算法技巧總結》、《JavaScript遍歷算法與技巧總結》及《JavaScript數(shù)學運算用法總結》
希望本文所述對大家JavaScript程序設計有所幫助。
- JS面向對象基礎講解(工廠模式、構造函數(shù)模式、原型模式、混合模式、動態(tài)原型模式)
- js面向對象之常見創(chuàng)建對象的幾種方式(工廠模式、構造函數(shù)模式、原型模式)
- JavaScript繼承基礎講解(原型鏈、借用構造函數(shù)、混合模式、原型式繼承、寄生式繼承、寄生組合式繼承)
- 詳解JavaScript中的構造器Constructor模式
- 構造函數(shù)+原型模式構造js自定義對象(最通用)
- javascript組合使用構造函數(shù)模式和原型模式實例
- javascript設計模式之對象工廠函數(shù)與構造函數(shù)詳解
- JavaScript構造函數(shù)詳解
- JS特殊函數(shù)(Function()構造函數(shù)、函數(shù)直接量)區(qū)別介紹
- 深入理解javascript構造函數(shù)和原型對象
- JavaScript中的普通函數(shù)與構造函數(shù)比較
相關文章
微信小程序 多行文本顯示...+顯示更多按鈕和收起更多按鈕功能
這篇文章主要介紹了微信小程序多行文本顯示...+顯示更多按鈕和收起更多按鈕,代碼簡單易懂,非常不錯,具有一定的參考借鑒價值,需要的朋友可以參考下2019-09-09javascript類型系統(tǒng)_正則表達式RegExp類型詳解
下面小編就為大家?guī)硪黄猨avascript類型系統(tǒng)_正則表達式RegExp類型詳解。小編覺得挺不錯的,現(xiàn)在就分享給大家,也給大家做個參考。一起跟隨小編過來看看吧2016-06-06