繼承
構造函數(shù)繼承:只能繼承實例的屬性和方法,不能繼承原型下的屬性和方法。
function Father(){}
function Son(){
在子類中定義一個實例屬性,值指向父類
this.parent = Father;
在子類中執(zhí)行父類的功能
this.parent();
delete this.parent;
}
call和apply
和構造函數(shù)繼承一樣,只能繼承實例的,不能繼承原型的。
call:父類構造函數(shù).call(this,參數(shù)1,參數(shù)2....) 通過call方式在子類中調用父類構造函數(shù),讓父類中的this指向子類的執(zhí)行環(huán)境
call方法第一個參數(shù):改變父類中的this指向
第二個參數(shù):繼承屬性傳參,個數(shù)為單個值,如果有多個,用逗號隔開,個數(shù)不固定
apply:繼承原理同call
apply與call的區(qū)別
apply的第二個參數(shù)要求是一個數(shù)組,可以使用arguments代替
call的第二個參數(shù)個數(shù)不固定
可以添加自己的獨特的屬性,父類不受影響
apply和call一樣,但傳參方式不一樣
原型鏈繼承
子類.prototype = new 父類()
將父類的實例對象賦值給子類的原型對象。繼承了父類的實例屬性和方法,也繼承了父類原型下的屬性和方法,但是無法傳參,也就無法再通過子類創(chuàng)建不同的實例對象
子類沒有實例屬性和方法、父類所有的屬性和方法都繼承到了子類的原型對象下。子類的constructor指向父類
組合繼承
通過call或apply或者構造函數(shù)繼承的方式,
實例的屬性和方法繼承在子類的實例對象中,再通過原型鏈繼承方式,
父級函數(shù)的全部(原型和實例)繼承在子類原型下
缺點:
1,父類執(zhí)行了兩次,子類原型下多了一些多余的屬性和方法(原父類的實例屬性和方法)
2,子類原型對象下的constructor的指向變成了父類
寄生組合繼承:
通過call或apply或者構造函數(shù)繼承的方式,實例的屬性和方法繼承在子類的實例對象中
使用Son.prototype = Object.create(Father.prototype);
把父類的原型下的方法繼承到子類型的原型下
把constructor的指向強制轉換成子類
Son.prototype.constructor = Son;
寄生組合繼承的封裝:
getProto(Son,Father);
function getProto(subType,supType){
var faObj = Object.create(supType.prototype);
faObj.constructor = subType;
subType.prototype = faObj;
}
ES6繼承,表現(xiàn)形式與寄生組合繼承一樣
super(參數(shù)1,參數(shù)2)方法,參數(shù)1,和參數(shù)2是父類的參數(shù)
class Father{
constructor(name){
this.name = name;
}
run(){
alert(this.name)
}
}
class Son extends Father{
constructor(name,age){
super(name); //先繼承,后定義自己的屬性。
this.age = age;
}
}