摘要:例如假如定義第二個子類然后在第一個子類中重新定義方法最后的輸出結果是由此可以看出,中的方法也發生了改變,如果將替換成方法,就不會存在這樣的問題。
前言
最近一直在回顧js繼承方式,在閱讀《高級程序設計》第3版 的時候遇到一個問題,下面僅個人看法,如果有理解錯誤或者不同看法,歡迎一起探討:
正文何謂寄生組合繼承,實質上分為兩步:
將父類的原型對象賦值給子類的原型對象
將子類原型對象中的constructor指針指向子類構造函數
這樣就實現了繼承,具體代碼如下所示(書中原代碼):
function SuperType(name){ this.name = name; } SuperType.prototype.sayName = function(){ console.log(this.name); } function SubType(name, age){ SuperType.call(this, name); this.age = age; } function inheritPrototype(subType, superType){ const subPrototype = Object(superType.prototype); subPrototype.constructor = SubType; subType.prototype = subPrototype; } inheritPrototype(SubType, SuperType); SubType.prototype.sayAge = function(){ console.log(this.age); } const sub_1 = new SubType("liumin", "23"); sub_1.sayName(); sub_1.sayAge();
在inheritPrototype函數當中正是完成了上面的兩個步驟,但是注意這里是通過Object函數創建一個對象賦值給subPrototype的,接下來我們了解一下Object函數
Object函數為給定值創建一個對象包裝器,如果傳入的是undefined 或者 null,則返回一個空對象;否則返回一個給定值對應類型的對象;
console.log(Object(undefined)); console.log(Object(null)); console.log(Object("123")); console.log(Object(123));
輸出結果是:
如果傳入的參數是一個對象,那么通過Object返回的則是對這個對象的引用,如下所示:
const person = { name:"xiaohong", age:"23", grade:"12", } const anotherPerson = Object(person); console.log(anotherPerson === person);
輸出結果:
person和anotherPerson引用的是同一塊內存地址,這與Object.create(obj)是有差別的,Object.create(obj)是在內存中新開辟一個空間
如果在上述的繼承方式中存在一個問題,如果之后通過子類的原型對象對父類中的sayName方法進行重新定義,這時候就會修改父類中的sayName方法,從而繼承父類的其他子類中的sayName方法也就會被篡改掉,造成混亂。
例如:
假如定義第二個子類——SubTypeCopy:
function SubTypeCopy(name, height){ SuperType.call(this, name); this.height = height; } inheritPrototype(SubTypeCopy, SuperType);
然后在第一個子類中重新定義sayName方法:
SubType.prototype.sayName = function(){ console.log(`my name is:${this.name}`); } const sub_1 = new SubType("liumin", "23"); const sub_2 = new SubTypeCopy("liujie","180"); sub_1.sayName(); sub_2.sayName();
最后的輸出結果是:
由此可以看出,SubTypeCopy中的sayName方法也發生了改變,如果將Object替換成Object.create(obj)方法,就不會存在這樣的問題。
文章版權歸作者所有,未經允許請勿轉載,若此文章存在違規行為,您可以聯系管理員刪除。
轉載請注明本文地址:http://m.specialneedsforspecialkids.com/yun/94824.html
摘要:下面來看一個例子繼承屬性繼承方法在這個例子中構造函數定義了兩個屬性和。組合繼承最大的問題就是無論什么情況下都會調用兩次超類型構造函數一次是在創建子類型原型的時候另一次是在子類型構造函數內部。 組合繼承 組合繼承(combination inheritance),有時候也叫做偽經典繼承,指的是將原型鏈和借用構造函數的技術組合到一塊,從而發揮二者之長的一種繼承模式。其背后的思路是使用原型鏈...
摘要:高程第六章繼承理解與實踐昨日細細的讀了一遍高程現在寫篇文章來鞏固下認知吧讀首先是從中讀到了什么我自己也在讀書的時候用筆記下了各個部分的點現在等于閱讀筆記回憶下書本理解基礎第五版中規定了兩種屬性數據屬性訪問器屬性數據屬性包含一個數據值的位 JavaScript高程第六章:繼承-理解與實踐昨日細細的讀了一遍JavaScript高程,現在寫篇文章來鞏固下認知吧. 讀 首先是從中讀到了什么,我...
摘要:高程讀書筆記第六章理解對象創建自定義對象的方式有創建一個實例,然后為它添加屬性和方法。創建了自定義的構造函數之后,其原型對象默認只會取得屬性至于其他方法都是從繼承而來的。 JS高程讀書筆記--第六章 理解對象 創建自定義對象的方式有創建一個Object實例,然后為它添加屬性和方法。還可用創建對象字面量的方式 屬性類型 ECMAScript在定義只有內部采用的特性時,描述了屬性的各種特征...
摘要:對于采用這種模式的對象,還可以使用操作符確定它的類型寄生構造函數模式通常,在前述的幾種模式都不適用的情況下,可以使用寄生構造函數模式。這個模式可以在特殊的情況下用來為對象創建構造函數。 ECMA-262把對象定義為:無序屬性的集合,其屬性可以包含基本值、對象或者函數。嚴格來講,這就相當于說對象是一組沒有特定順序的值。 1 理解對象 創建對象: var person = new Obje...
閱讀 3076·2021-11-24 11:14
閱讀 3514·2021-11-22 15:22
閱讀 3210·2021-09-27 13:36
閱讀 720·2021-08-31 14:29
閱讀 1334·2019-08-30 15:55
閱讀 1765·2019-08-29 17:29
閱讀 1151·2019-08-29 16:24
閱讀 2414·2019-08-26 13:48