Javascript之深入淺出prototype
我們先來講一個故事,一個大大的池塘,里面有很多魚。這是屬于我們大家的池塘所以里面的魚我們都可以吃,但是我們也會從集市買一些魚放在家里,那么放在家里的魚肯定是屬于我們私人的,外人是不會擁有的。那么在js里我們就把這個池塘稱為原型對象,池塘里面我們所共享的魚稱為原型中的屬性及方法,而我們自己的魚稱為構(gòu)造函數(shù)中的屬性及方法,我們是什么呢?對了,我們是對象的實例。
以上是為了讓大家能夠趣味性的對prototype有一個概念,接下來就通過代碼具體總結(jié)一下prototype~
一、理解prototype
我們創(chuàng)建的每一個函數(shù)都有一個prototype屬性,這個屬性是一個指向?qū)ο蟮闹羔槨?/p>
構(gòu)建對象中有一種模式叫做原型模式,意思是將對象實例所不可共享的屬性及方法定義在構(gòu)造函數(shù)中,而將可共享的屬性及方法放在原型對象中,也就是prototype指向的對象中。以下是用原型模式創(chuàng)建的一個對象:
function person(name, age) {
this.name = name;
this.age = age;
}
person.prototype = {
sayName: function() {
console.log(this.name);
}
};
var p1 = new person("Wind", 20);
p1.sayName(); // "Wind"
var p2 = new person("Nic", 20);
p2.sayName(); // Nic
這里我將name、age屬性定義在構(gòu)造函數(shù)中,將sayName方法定義在原型中。所以p1和p2對象實例的內(nèi)存空間里面各有一份name和age,但是它們卻共享一份sayName方法,意思是它們調(diào)用的sayName方法是同一個。
試想如果我們不用prototype,而是直接將sayName寫進構(gòu)造函數(shù)呢?
那么p1和p2中將各有一份sayName,這樣浪費內(nèi)存空間,所以用prototype的好處之一:提高了代碼的復用性,減少內(nèi)存。
在了解原型對象的同時我們還有一個小知識要明白:每當代碼讀取一個對象屬性的時候會執(zhí)行一次搜索,搜索目標是給定名字的屬性,搜索路徑為:
對象實例本身---->原型對象---->對象所繼承的父類對象---->父類對象原型...---->原型鏈末端
二、prototype的注意點
1、不可變性:盡管prototype是共享的,但不能通過對象實例重寫原型中的值,但是可以由對象統(tǒng)一改。通俗一點:只能爸爸統(tǒng)一改,不能兒子改。(這也和類型有關系,孩子不能改變基本類型的值,但是可以改變對象,比如數(shù)組)
基本類型:
function person() {}
person.prototype = {
num: 0
};
var p1 = new person();
var p2 = new person();
p1.num++;
p2.num; // 0
非基本類型:
function person() {}
person.prototype = {
num: [1,2,3]
};
var p1 = new person();
var p2 = new person();
p1.num[2] = 8;
p2.num; // [1, 2, 8] 改變了
2、同名覆蓋性:如果我們在實例中添加了一個與原型屬性同名的屬性,那么該屬性會創(chuàng)建到對象實例中并且會覆蓋掉原型中的相應屬性。
function person(name) {
this.name = name;
}
person.prototype = {
age: 18 9 };
var p1 = new person("Wind");
var p2 = new person("Nic");
p1.age = 20;
p1.age; // 20
p2.age; // 18
3、使用對象字面量創(chuàng)建原型方法,會切斷之前的鏈而重寫原型鏈
function person(name) {
this.name = name;
}
person.prototype = {
sayName: function() {
console.log(this.name);
}
};
var p1 = new person("Wind");
person.prototype = {
age = 20
};
p1.sayName(); // error
因為prototype指針指向了一個新的對象,切斷了構(gòu)造函數(shù)與之前的prototype舊對象的聯(lián)系,所以p1不能調(diào)用了它。那么p1調(diào)用新對象的屬性呢?
p1.age; // error
所以我做了一個大膽的猜測,就是以前包含sayName的舊對象被“拋棄”了,也就是被內(nèi)存回收了,然而p1的prototype指針指向的依舊是舊對象,所以會產(chǎn)生error。
三、總結(jié)
prototype的用法:構(gòu)造函數(shù)模型用于定義實例的屬性,而原型模型用于定義方法和共享的屬性。
以上就是本文的全部內(nèi)容,希望本文的內(nèi)容對大家的學習或者工作能帶來一定的幫助,同時也希望多多支持腳本之家!
相關文章
AJAX跨域請求json數(shù)據(jù)的實現(xiàn)方法
這篇文章介紹了AJAX跨域請求json數(shù)據(jù)的實現(xiàn)方法,有需要的朋友可以參考一下2013-11-11
Net微信網(wǎng)頁開發(fā) 使用微信JS-SDK獲取當前地理位置過程詳解
這篇文章主要介紹了Net微信網(wǎng)頁開發(fā) 使用微信JS-SDK獲取當前地理位置過程詳解,文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友可以參考下2019-08-08
gameboy網(wǎng)頁闖關游戲(riddle webgame)--仿微信聊天的前端頁面設計和難點
本文講如何在網(wǎng)頁端實現(xiàn)一個仿微信的聊天窗口界面, 以及其中涉及到的一些技術(shù)點. 對gameboy闖關游戲相關知識感興趣的朋友參考下2016-02-02
JavaScript實現(xiàn)淘寶購物件數(shù)選擇
這篇文章主要為大家詳細介紹了JavaScript實現(xiàn)淘寶購物件數(shù)的選擇,文中示例代碼介紹的非常詳細,具有一定的參考價值,感興趣的小伙伴們可以參考一下2022-08-08
JavaScript中有關一個數(shù)組中最大值和最小值及它們的下表的輸出的解決辦法
這篇文章主要介紹了JavaScript中有關一個數(shù)組中最大值和最小值及它們的下表的輸出的一種解決辦法,本文還給大家介紹了js快速獲取數(shù)組中最大值和最小值的方法,非常不錯,需要的朋友可以參考下2016-07-07

