JavaScript是如何實(shí)現(xiàn)繼承的(六種方式)
前言:大多OO語(yǔ)言都支持兩種繼承方式: 接口繼承和實(shí)現(xiàn)繼承 ,而ECMAScript中無(wú)法實(shí)現(xiàn)接口繼承,ECMAScript只支持實(shí)現(xiàn)繼承,而且其實(shí)現(xiàn)繼承主要是依靠 原型鏈 來(lái)實(shí)現(xiàn)。
1.原型鏈
基本思想:利用原型讓一個(gè)引用類型繼承另外一個(gè)引用類型的屬性和方法。
構(gòu)造函數(shù),原型,實(shí)例之間的關(guān)系:每個(gè)構(gòu)造函數(shù)都有一個(gè)原型對(duì)象,原型對(duì)象包含一個(gè)指向構(gòu)造函數(shù)的指針,而實(shí)例都包含一個(gè)指向原型對(duì)象的內(nèi)部指針。
原型鏈實(shí)現(xiàn)繼承例子:
function SuperType() { this.property = true; } SuperType.prototype.getSuperValue = function() { return this.property; } function subType() { this.property = false; } //繼承了SuperType SubType.prototype = new SuperType(); SubType.prototype.getSubValue = function (){ return this.property; } var instance = new SubType(); console.log(instance.getSuperValue());//true
2.借用構(gòu)造函數(shù)
基本思想:在子類型構(gòu)造函數(shù)的內(nèi)部調(diào)用超類構(gòu)造函數(shù),通過(guò)使用call()和apply()方法可以在新創(chuàng)建的對(duì)象上執(zhí)行構(gòu)造函數(shù)。
例子:
function SuperType() { this.colors = ["red","blue","green"]; } function SubType() { SuperType.call(this);//繼承了SuperType } var instance1 = new SubType(); instance1.colors.push("black"); console.log(instance1.colors);//"red","blue","green","black" var instance2 = new SubType(); console.log(instance2.colors);//"red","blue","green"
3.組合繼承
基本思想:將原型鏈和借用構(gòu)造函數(shù)的技術(shù)組合在一塊,從而發(fā)揮兩者之長(zhǎng)的一種繼承模式。
例子:
function SuperType(name) { this.name = name; this.colors = ["red","blue","green"]; } SuperType.prototype.sayName = function() { console.log(this.name); } function SubType(name, age) { SuperType.call(this,name);//繼承屬性 this.age = age; } //繼承方法 SubType.prototype = new SuperType(); Subtype.prototype.constructor = Subtype; Subtype.prototype.sayAge = function() { console.log(this.age); } var instance1 = new SubType("EvanChen",18); instance1.colors.push("black"); consol.log(instance1.colors);//"red","blue","green","black" instance1.sayName();//"EvanChen" instance1.sayAge();//18 var instance2 = new SubType("EvanChen666",20); console.log(instance2.colors);//"red","blue","green" instance2.sayName();//"EvanChen666" instance2.sayAge();//20
4.原型式繼承
基本想法:借助原型可以基于已有的對(duì)象創(chuàng)建新對(duì)象,同時(shí)還不必須因此創(chuàng)建自定義的類型。
原型式繼承的思想可用以下函數(shù)來(lái)說(shuō)明:
function object(o) { function F(){} F.prototype = o; return new F(); }
例子:
var person = { name:"EvanChen", friends:["Shelby","Court","Van"]; }; var anotherPerson = object(person); anotherPerson.name = "Greg"; anotherPerson.friends.push("Rob"); var yetAnotherPerson = object(person); yetAnotherPerson.name = "Linda"; yetAnotherPerson.friends.push("Barbie"); console.log(person.friends);//"Shelby","Court","Van","Rob","Barbie"
ECMAScript5通過(guò)新增Object.create()方法規(guī)范化了原型式繼承,這個(gè)方法接收兩個(gè)參數(shù):一個(gè)用作新對(duì)象原型的對(duì)象和一個(gè)作為新對(duì)象定義額外屬性的對(duì)象。
var person = { name:"EvanChen", friends:["Shelby","Court","Van"]; }; var anotherPerson = Object.create(person); anotherPerson.name = "Greg"; anotherPerson.friends.push("Rob"); var yetAnotherPerson = Object.create(person); yetAnotherPerson.name = "Linda"; yetAnotherPerson.friends.push("Barbie"); console.log(person.friends);//"Shelby","Court","Van","Rob","Barbie"
5.寄生式繼承
基本思想:創(chuàng)建一個(gè)僅用于封裝繼承過(guò)程的函數(shù),該函數(shù)在內(nèi)部以某種方式來(lái)增強(qiáng)對(duì)象,最后再像真正是它做了所有工作一樣返回對(duì)象。
例子:
function createAnother(original) { var clone = object(original); clone.sayHi = function () { alert("hi"); }; return clone; } var person = { name:"EvanChen", friends:["Shelby","Court","Van"]; }; var anotherPerson = createAnother(person); anotherPerson.sayHi();///"hi"
6.寄生組合式繼承
基本思想:通過(guò)借用函數(shù)來(lái)繼承屬性,通過(guò)原型鏈的混成形式來(lái)繼承方法
其基本模型如下所示:
function inheritProperty(subType, superType) { var prototype = object(superType.prototype);//創(chuàng)建對(duì)象 prototype.constructor = subType;//增強(qiáng)對(duì)象 subType.prototype = prototype;//指定對(duì)象 }
例子:
function SuperType(name){ this.name = name; this.colors = ["red","blue","green"]; } SuperType.prototype.sayName = function (){ alert(this.name); }; function SubType(name,age){ SuperType.call(this,name); this.age = age; } inheritProperty(SubType,SuperType); SubType.prototype.sayAge = function() { alert(this.age); }
以上內(nèi)容給大家介紹了javascript實(shí)現(xiàn)繼承的六種方式,希望對(duì)大家有所幫助!
相關(guān)文章
一文讓你徹底弄懂js中undefined和null的區(qū)別
JavaScript是一門動(dòng)態(tài)類型語(yǔ)言,元素除了表示存在的空值外,還有可能根本就不存在,這就是undefined存在的原因,這篇文章主要給大家介紹了關(guān)于undefined和null區(qū)別的相關(guān)資料,需要的朋友可以參考下2022-03-03js數(shù)組循環(huán)遍歷數(shù)組內(nèi)所有元素的方法
在js中數(shù)組遍歷最簡(jiǎn)單的辦法就是使用for然后再利用arr.length長(zhǎng)度作為for最大限度值即可解決了,下面我們來(lái)看看一些有用的實(shí)例2014-01-01打造通用的勻速運(yùn)動(dòng)框架(實(shí)例講解)
下面小編就為大家?guī)?lái)一篇打造通用的勻速運(yùn)動(dòng)框架(實(shí)例講解)。小編覺(jué)得挺不錯(cuò)的,現(xiàn)在就分享給大家,也給大家做個(gè)參考。一起跟隨小編過(guò)來(lái)看看吧2017-10-10JavaScript屏蔽Backspace鍵的實(shí)現(xiàn)代碼
這篇文章主要介紹了JavaScript屏蔽Backspace鍵的實(shí)現(xiàn)代碼,非常不錯(cuò),具有參考借鑒價(jià)值,需要的朋友可以參考下2017-11-11微信小程序注冊(cè)60s倒計(jì)時(shí)功能 使用JS實(shí)現(xiàn)注冊(cè)60s倒計(jì)時(shí)功能
這篇文章主要介紹了微信小程序注冊(cè)60s倒計(jì)時(shí)功能,以及使用JS實(shí)現(xiàn)注冊(cè)60s倒計(jì)時(shí)功能,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2017-08-08