前言:我們創(chuàng)建的每個函數都有一個prototype屬性,這個屬性是一個指針,指向的是一個對象椿息,這個對象的作用是包含由該構造函數創(chuàng)建實例共享的屬性和方法悠反。通過字面意思來了解,prototype是通過構造函數創(chuàng)建對象實例的原型對象注盈,使用原型對象的好處就是可以讓所有的實例共享它所包含的屬性和方法晃危,這樣就不會像構造函數模式,在每次創(chuàng)建一個新的實例后都會將內部的方法重新創(chuàng)建一遍老客。如下例子圖1-1:
我們可以看到在Person構造函數的prototype原型上面我們掛載了屬性和方法僚饭,我們在創(chuàng)建實例的時候纠俭,每個實例都會有相同的屬性和方法,與構造函數模式不同的是這些屬性和實例都是共享的浪慌。
什么是原型對象冤荆?
在我們創(chuàng)建每一個函數的時候,都會根據特定的規(guī)則為該函數創(chuàng)建一個prototype屬性权纤,這個屬性指向的是函數的原型對象钓简。在每個函數的prototype屬性下面也會自動獲得一個constructor(構造函數)屬性。我們可以打印一下Person.prototype.constructor汹想,如下2-1:
創(chuàng)建自定義的構造函數后外邓,其原型對象只會去得到constructor屬性,其他的方法都是從Object上繼承來的古掏。當調用構造函數創(chuàng)建一個對象的時候损话,這個對象內部將會有個一指針指向的是構造函數的原型對象上,我們管這個指正叫做[[Prototype]]槽唾,在chrome等瀏覽器中打印出來顯示的是__proto__丧枪,我們要知道這個是連接實例對象和構造函數原型對象的。如圖3-1和3-2:
我們可以看到上圖中庞萍,實例對象的__proto__打印的是構造函數的原型對象拧烦,原型對象上也有一個constructor屬性,指向的是構造函數钝计。
這里我們介紹兩個方法:isPrototypeOf() ?/ ?Object.getPrototypeOf()恋博,根據英文的意思,第一個就是判斷某個原型對象是不是某個實例[[Prototype]]指向的原型對象私恬,第二個是用來獲得某個實例對象的原型對象债沮。如下圖代碼4-1和4-2:
之前我們不是說通過原型構造對象,所有的對象共享原型對象上的方法和屬性么本鸣,那么這是怎么共享的呢疫衩?當我們要讀取某個實例對象上的某個屬性或者方法的時候,它會在當前的對象上進行搜索永高,如果找到了那么就返回這個屬性或者方法隧土,如果沒有找到,就會搜索指針指向的原型對象命爬,在該原型對象上找到的話就會返回這個原型對象上的屬性值和方法....就這樣會一直找到Object對象上曹傀。那么反過來理解,如果我們在實例對象上新增一個同原型對象上一樣的name屬性饲宛,那么當讀取該name屬性的時候皆愉,就會讀取到當前實例對象上為止,就不會繼續(xù)往上讀取了。
這里我們再次介紹一個方法:hasOwnProperty()幕庐,該方法可以檢測一個屬性是否存在于實例中久锥,還是存在于原型中(該方法繼承于Object)。如圖5-1例子:
如例子所示异剥,hasOwnproperty方法是是用來判斷屬性或者方法是不是實例屬性方法還是原型上的屬性方法瑟由。
這個我們拋出一個問題,如何定義一個屬性是在實例對象上的還是在原型對象上的冤寿?那么我們要通過in操作符和hasOwnProperty()方法一起來判斷了歹苦,in操作符可以在for-in循環(huán)中使用,也可以單獨使用督怜,單獨使用的時候殴瘦,如果某個屬性在實例對象上或者原型對象上都返回TRUE,根據之前的例子可以知道号杠,hasOwnProperty()方法只會在屬性在實例上的時候才返回TRUE蚪腋,那么當操作符in返回TRUE的時候,hasOwnproperty()返回FALSE的時候姨蟋,可以判斷當前屬性是在原型對象上的屉凯,而不是在實例對象上的。
有些困了芬探,今天就復習到這里神得,明天進一步更新厘惦,更多的內容可以看js高級程序設計....