js 对象创建及其继承的方法
重新看紅皮書,覺得很多知識(shí)多看幾遍確實(shí)是能看的更明白些。今天重溫了一下對(duì)象創(chuàng)建和繼承,就稍微記下來,鞏固一下。
js是面向?qū)ο蟮木幊陶Z言,ECMA-262吧對(duì)象定義為:“無序?qū)傩缘募?#xff0c;其屬性可以包含基本值,對(duì)象或者函數(shù)”。每個(gè)對(duì)象都是基于一個(gè)引用類型創(chuàng)建的,這個(gè)引用類型可以是原生類型,也可以是自定義的。
一,講講創(chuàng)建對(duì)象的幾個(gè)方法
1. var person = new Object();?
2. var person = {};
3. 工廠模式
4. 構(gòu)造函數(shù)模式
5. 原型模式
6. 組合使用構(gòu)造函數(shù)模式和冤案型模式
7. 動(dòng)態(tài)原型模式
8.等等......
這里著重記一下構(gòu)造模式和原型模式,畢竟之后的模式和繼承方法都是由于這兩個(gè)的優(yōu)缺點(diǎn)借鑒而來。
4.構(gòu)造函數(shù)模式
function Person(name,age,job){
this.name = name;
this.age = age;
this.job = job;
this.sayName = function(){
console.log(this.name);
};
}
var person1 = new Person('niko','19','FE');
?這種方式創(chuàng)建對(duì)象,可以將它的實(shí)例化標(biāo)識(shí)為一中特定類型。及實(shí)例可以通過 instanceof 或者constructor 來檢測(cè)對(duì)象的類型。缺點(diǎn)是無法完成方法的復(fù)用,即每個(gè)方法都需要在實(shí)例化上重新創(chuàng)建。
5.原型模式
我們自然是希望創(chuàng)建對(duì)象時(shí)可以共享某些屬性和方法,搞這個(gè)原型模式挺拿手的~~~來露個(gè)臉。簡單的說,我們創(chuàng)建的每個(gè)函數(shù)都有一個(gè)prototype屬性,這個(gè)prototype屬性是一個(gè)指針,指向一個(gè)對(duì)象,這個(gè)對(duì)象里面放著創(chuàng)建的這個(gè)對(duì)象實(shí)例的原型對(duì)象。原型對(duì)象,即是包含所有實(shí)例都共享的屬性和方法。默認(rèn)情況下,所有原型對(duì)象都自動(dòng)獲得一個(gè)constructor屬性,這個(gè)屬性包含一個(gè)指向prototype屬性所在函數(shù)的指針。繞來繞去估計(jì)就暈了,來個(gè)圖解釋一下。
通過原型模式創(chuàng)建對(duì)象之后,是可以順順利利的完成屬性和方法的共享,但是也是有弊端的如果包含引用類型的值,那么實(shí)例化的某一個(gè)對(duì)象對(duì)這個(gè)值進(jìn)行操作,就會(huì)修改原型里的值,這樣問題就比較麻煩了。所以組合模式就出現(xiàn)了,及用構(gòu)造函數(shù)來創(chuàng)建屬性,用原型模式來創(chuàng)建共享方法。
7.動(dòng)態(tài)原型模式,就是把所有信息封裝到函數(shù)里看著會(huì)簡潔好多,也是組合了構(gòu)造函數(shù)和原型模式的優(yōu)點(diǎn),在函數(shù)內(nèi)部初始化原型(僅僅在第一次運(yùn)行時(shí)初始化)。
function Person(name,age,job){
this.name = name;
this.age = age;
this.job = job;
if(typeof this.sayName!= "function"){
Person.prototype.sayName = function(){
console.log(this.name);
};
}
}
var person1 = new Person('niko','19','FE');
跟組合模式不同的是,初始化原型在函數(shù)內(nèi)部,并且如果有多個(gè)共享函數(shù)時(shí),只判斷一個(gè)就好~~看著簡潔那么一小丟~~對(duì)象創(chuàng)建就寫到這,接下來寫一下繼承啦啦啦啦~
二,常見的繼承方式
1.原型鏈
2.借用構(gòu)造函數(shù)
3.組合繼承
4.組合寄生式繼承
5.原型式,寄生式..
挑幾個(gè)重要的講吧,重要的就是掌握原型鏈的原理,以及構(gòu)造函數(shù)繼承方式,組合是采取了這兩個(gè)優(yōu)缺點(diǎn)進(jìn)行優(yōu)化,組合寄生則是針對(duì)組合繼承進(jìn)行的優(yōu)化。原型、寄生式是對(duì)一個(gè)相對(duì)的對(duì)象來創(chuàng)建另一個(gè),沒怎么碰到就不講了。
1.原型鏈
原型鏈的主要思想就是讓一個(gè)引用類型繼承另一個(gè)引用類型的實(shí)例。原型對(duì)象將包含一個(gè)指向另一個(gè)原型的指針,另一個(gè)原型中也包含指向另一個(gè)構(gòu)造函數(shù)的指針。層層遞進(jìn)之后,形成原型鏈。
function SuperType(){
this.property = true;
}
SuperType.prototype.getSuperValue = function(){
return this.property;
};
function Subtype(){
this.subproperty = false;
}
Subtype.prototype.getSubValue = function(){
return this.subproperty;
}
Subtype.prototype.getSubValue = function(){
return this.subproperty;
};
var instance = new Subtype();
啊,寫到一半突然要閉館了閉館了閉館了=.=淚奔一下 ,中間詳細(xì)就不解釋了,看懂這個(gè)圖就沒啥大問題了~原型鏈的問題就是,共享引用類型值的時(shí)候,修改一個(gè)實(shí)例就會(huì)修改原型。
2.借用構(gòu)造函數(shù)
這個(gè)方法就是在子類構(gòu)造函數(shù)中調(diào)用超類的構(gòu)造函數(shù)。
function SuperType(name){
this.name = name;
}
function SubType(){
SuperType.call(this,'niko'); //在this的作用域中調(diào)用SuperType()
}
var instance = new SubType();
這種方式不像原型繼承,相當(dāng)于在子類的作用域中吧超類的屬性完完全全復(fù)制了一份。因?yàn)椴皇且玫闹羔?#xff0c;所以,即使是引用類型的屬性值,每個(gè)實(shí)例都會(huì)復(fù)制一份屬性值,所以不會(huì)有什么問題噠~~~而且借用構(gòu)造函數(shù)模式可以在子類中傳參。
3.組合繼承就是兼顧了原型模式和借用構(gòu)造函數(shù)模式的優(yōu)缺點(diǎn)。既可以共享方法,也可以讓不同的實(shí)例分別有自己的屬性。
??
function SuperType(name){
this.name = name;
this.colors = ['red','blue','orange'];
}
SuperType.prototype.sayName = function(){
console.log(this.name);
}
function SubType(name,age){
//繼承屬性
SuperType.call(this,name); //第二次調(diào)用SuperType()
this.age = age;
}
SubType.prototype.sayAge = function(){
console.log(this.age);
}
//繼承方法
SubType.prototype = new SuprType(); //第一次調(diào)用SuperType();
var instance = new Subtype('niko',34);
如圖所示,第一次調(diào)超類的時(shí)候,SubType.prototype得到兩個(gè)屬性:name,colors。調(diào)用Subtype構(gòu)造函數(shù)時(shí),第二次調(diào)用超類,在新對(duì)象上創(chuàng)建實(shí)例屬性:name,colors。這兩個(gè)實(shí)例屬性屏蔽了原型中的屬性。
這種方法可以達(dá)到既可以共享方法,也可以有自己的實(shí)例屬性,但是調(diào)用兩次超類的構(gòu)造函數(shù)。
4.寄生組合式繼承
為了解決組合式的缺點(diǎn),寄生組合式這個(gè)超級(jí)大Boss上場(chǎng)了。
大體思路還是借用構(gòu)造函數(shù)來繼承屬性,用原型鏈的混成方法機(jī)場(chǎng)方法。與組合 方式不同的是,沒有在子類中調(diào)用超類,而是取得了一個(gè)超類的副本。
function inhertiPrototype(subType,superType){
var prototype = object(superType.prototype); //創(chuàng)建對(duì)象
prototype.constructor = subType; //增強(qiáng)對(duì)象
subType.prototype = prototype; //指定對(duì)象
}
?
?
?
?
?
?
?
?
轉(zhuǎn)載于:https://www.cnblogs.com/echo-yaonie/p/4639396.html
總結(jié)
以上是生活随笔為你收集整理的js 对象创建及其继承的方法的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: C++实现glut绘制点、直线、多边形、
- 下一篇: 【第一行代码笔记】(一)