一、構造函數綁定
使用call或apply方法,將父對象的構造函數綁定在子對象上。
function Animal(){
this.species = "動物";
}
function Cat(name,color){
Animal.apply(this,arguments);
this.name=name;
this.color=color;
}
var cat = new Cat('小白','白');
console.log(cat.species);
二、prototype模式
如果貓的prototype對象,指向一個Animal的實例,那麼所有貓的實例,就能繼承Animal
function Animal(){
this.species = "動物";
}
function Cat(name,color){
this.name=name;
this.color=color;
}
Cat.prototype = new Animal();
Cat.prototype.constructor = Cat;
var cat = new Cat('小白','白');
console.log(cat.species);
將Cat的prototype的對象指向一個Animal實例,它相當於安全刪除了prototype原來的值,給它賦予了一個新值。
Cat.prototype = new Animal();
任何一個prototype對象都有一個constructor屬性,指向它的構造函數,如果沒有Cat.prototype = new Animal(),Cat.prototype.constructor是指向Cat的,加上這一行,Cat.prototype.constructor指向Animal。這回導致繼承紊亂,必須手動矯正,將Cat的prototype對象的constructor的值改爲Cat
Cat.prototype.constructor = Cat
三、直接繼承prototype
function Animal(){}
Animal.prototype.species = '動物';
function Cat(name,color){
this.name=name;
this.color=color;
}
Cat.prototype = Animal.prototype;
Cat.prototype.constructor = Cat;
console.log('cat',Cat.prototype.constructor);
console.log('animal',Animal.prototype.constructor);
與前一種做法相比,這種的優點是效率比較高(不用創建Animal實例),缺點是Animal.prototype和Cat.prototype指向了同一個對象,任何對Cat.prototype的修改都會影響到Animal.prototype。
Cat.prototype.constructor = Cat;
實際上把Animal的prototype對象的constructor屬性也改掉了
console.log('cat',Cat.prototype.constructor); //Cat
console.log('animal',Animal.prototype.constructor); //Cat
四、利用空對象作爲中介
function Animal(){}
Animal.prototype.species = '動物'
function Cat(name,color){
this.name=name;
this.color=color;
}
var F = function(){}
F.prototype = Animal.prototype;
Cat.prototype = new F();
Cat.prototype.constructor = Cat;
var cat = new Cat('小白','白');
console.log(cat.species);
console.log(Animal.prototype.constructor); // Animal
F是空對象,所以幾乎不佔內存,修改Cat的prototype對象就不會影響到Animal的prototype對象
可以將上述方法封裝成一個函數
function extend(child,parent){
var F = function(){};
F.prototype = parent.prototype;
child.prototype = new F();
child.prototype.constructor = Cat;
}
使用方法:
extend(Cat,Animal);
var cat = new Cat('小白','白');
console.log(cat.species);
五、拷貝繼承
首先把Animal上所有不變的屬性都放到prototype對象上,
function Animal(){}
Animal.prototype.species = '動物';
function Cat(name,color){
this.name=name;
this.color=color;
}
再寫一個函數實現拷貝的目的
function extend(child,parent){
var p = parent.prototype;
var c = child.prototype;
for(var i in p){
c[i] = p[i];
console.log(c[i]);
}
}
使用方法:
extend(Cat,Animal);
var cat = new Cat('小白','白');
console.log(cat.species);