摘要:原型與原型鏈一在了解原型之前需要提前了解的。構造函數能很好的解決這個問題。構造函數自定義構造函數,可以自定義對象類型的屬性和方法。二原型模式如下,與構造函數模式不同的是,原型模式的每個實例都是訪問同一屬性同一函數,,函數不用重新創建。
原型與原型鏈
一.在了解原型之前需要提前了解的。
1.工廠模式:創建一個函數,用特定的接口創建對象的細節。
//現在要創建兩個包含 “name”和“age”的對象, let tom ={name:"Tom",age:16} let lily = { name : "Lily",age:18} ……//所示數量足夠具大 ,對象足夠大 ,會花費大量的時間。下面的工廠模式能 很好的解決這一問題
//工廠的就是只流水線不是所有都是要人工,節約人力成本。 function person(name,age){ let obj = {}; //創建一個對象 ; obj.name = name ; //為對象添加細節 obj.age = age ; obg.sayHello= function (){ alert ("Hello"+this.name) }; return obj;} //返回這個對象 let tom = person("Tom",16); let lily = person("Lily",18)
工廠函數的優勢:避免的大量的重復代碼;
工廠函數的劣勢:其創建的對象不能標志為一種特定的類型,沒有解決對象識別的問題,不知道對象的類型。構造函數能很好的解決這個問題。
2.構造函數:自定義構造函數,可以自定義對象類型的屬性和方法。
function Person(name,age){ this.name = name ; //為對象添加細節 this.age = age ; this.sayHello= function (){ alert ("Hello"+this.name) }; let tom = new Person("Tom",16); let lily =new Person("Lily",18)
new的過程做了三件事①創建了一個對象;②將this指向這個對象;③返回這個對象;
兩個實例對象都有一個屬性constructor(構造函數),指向Person;這就是可以通過constructor判斷對象類型的原理。
存在的問題:構造函數的每個方法都要在實例上重新創建一遍,雖然函數名是一樣的,但是不相等的。
二.原型模式
1.如下,與構造函數模式不同的是,原型模式的每個實例都是訪問同一屬性同一函數,,函數不用重新創建。
function Person () { this.x = 100; } Person.prototype.name = "Tom"; Person.prototype.age = 18; Person.prototype.sayHello = function (){ alert(`Hello${this.name}`) } let Tom = new Person() Tom.sayHello()
2.原型對象
①每個函數數據類型(普通函數,類)上,都有一個屬性,叫prototype,是一個對象,這個函數指向函數的原型對象;
②prototype這個對象上,自帶一個屬性,constructor指向當前這個類;
③當為實例添加屬性時,這個屬性會屏蔽原型對象中保存的同名屬性,但是事實阻止訪問,并沒有修改那個屬性,若將同名的實例屬性設置為null,同樣會屏蔽,但是若用delete,則可以刪除實例屬性,可以重新訪問原型中的屬性。
alert(Tom.age); //18 let Tom.age = 20; alert(Tom.age); //20 delete Tom.age; alert(Tom.age); //18
④屬性分為兩種,來自實例(或者是構造函數)或是原型,原型上的屬性和方法都是共有的,構造函數中的屬性方法都是私有的,構造函數中的this都是實例。為什么私有屬性(來自實例的屬性)的查找等級要高呢?這就涉及到原型鏈。
3.原型鏈:每個對象數據類型(普通對象,prototype,實例)都有一個屬性,叫做__proto__;
比如我們console.log(Tom.age)的查找過程是怎樣的呢?①首先在私有空間內查找age屬性,私有空間的屬性包括自身的屬性和從類那里繼承的屬性,
②找不到的話:通過__proto__去當前實例所屬類的原型上進行查找,找到的話,說明是共有屬性;
③還找不到的話:繼續通過__proto__去當前實例所屬類的原型進行查找,找不到將繼續通過__proto__一直找到Object。
④曲線①代表Person的原型對象;曲線②中,實例Tom通過__proto__指向Tom所屬類(Person)的原型(Person Prototype);曲線③中,Person的原型對象通過__proto__找到Person對象的所屬類,也就是Object(函數也是對象類,萬物皆對象),指向它的原型(ObjectPrototype) ;曲線5中,指向Obeject所屬類的原型,它的類就是它自己,所以此時不在有__proto__整個屬性查找結束,這就是原型鏈的查找過程。
⑤通過hasOwnProperty來判斷屬性,這個方法就是通過④中的查找過程,在基類Object中找到的。 判斷屬性是否在對象上“name” in Tom,其中in的查找過程也是通過上述的查找過程。
function hasPrototypeProperty(object,attr){ return !object.hasOwnProperty(attr) && (attr in object);}
4.關于原型需要注意的幾點
①使用簡單原型語法的時候,注意constructor的指向問題,
Person.prototype={ //此時constructor指向Object構造函數 name : "Tom", age:18 } Person.prototype={ //此時constructor指向Person constructor:Person, name : "Tom", age:18 }
②添加和修改原型的屬性和方法都能立即在所有對象實例中反應出來(即使先創建實例后修改原型);但是如果重寫整個原型對象,創建在前的實例并不能獲得重寫后的屬性或方法。這是因為重寫原型之后是新生成原型對象,和聲明在前的任何已經存在的實例都沒有關系。
文章版權歸作者所有,未經允許請勿轉載,若此文章存在違規行為,您可以聯系管理員刪除。
轉載請注明本文地址:http://m.specialneedsforspecialkids.com/yun/84318.html
摘要:原型鏈與繼承當談到繼承時,只有一種結構對象。如果對該圖不怎么理解,不要著急,繼續往下看基于原型鏈的繼承對象是動態的屬性包指其自己的屬性。當使用操作符來作用這個函數時,它就可以被稱為構造方法構造函數。 原型鏈與繼承 當談到繼承時,JavaScript 只有一種結構:對象。每個實例對象(object )都有一個私有屬性(稱之為proto)指向它的原型對象(prototype)。該原型對象也...
摘要:寫在前面如果說是一本武學典籍,那么原型鏈就是九陽神功。那么,如何修煉好中的九陽神功呢真正的功法大成的技術是從底層上去理解,那種工程師和碼農的區別就在于對底層的理解,當你寫完一行代碼,或者你遇見一個解決的速度取決于你對底層的理解。 寫在前面 如果說JavaScript是一本武學典籍,那么原型鏈就是九陽神功。在金庸的武俠小說里面,對九陽神功是這樣描述的:練成「九陽神功」后,會易筋洗髓;生出...
摘要:寫在前面如果說是一本武學典籍,那么原型鏈就是九陽神功。那么,如何修煉好中的九陽神功呢真正的功法大成的技術是從底層上去理解,那種工程師和碼農的區別就在于對底層的理解,當你寫完一行代碼,或者你遇見一個解決的速度取決于你對底層的理解。 寫在前面 如果說JavaScript是一本武學典籍,那么原型鏈就是九陽神功。在金庸的武俠小說里面,對九陽神功是這樣描述的:練成「九陽神功」后,會易筋洗髓;生出...
摘要:寫在前面如果說是一本武學典籍,那么原型鏈就是九陽神功。那么,如何修煉好中的九陽神功呢真正的功法大成的技術是從底層上去理解,那種工程師和碼農的區別就在于對底層的理解,當你寫完一行代碼,或者你遇見一個解決的速度取決于你對底層的理解。 寫在前面 如果說JavaScript是一本武學典籍,那么原型鏈就是九陽神功。在金庸的武俠小說里面,對九陽神功是這樣描述的:練成「九陽神功」后,會易筋洗髓;生出...
閱讀 2075·2023-04-25 17:48
閱讀 3586·2021-09-22 15:37
閱讀 2939·2021-09-22 15:36
閱讀 5997·2021-09-22 15:06
閱讀 1642·2019-08-30 15:53
閱讀 1428·2019-08-30 15:52
閱讀 713·2019-08-30 13:48
閱讀 1124·2019-08-30 12:44