js实现继承的数种方法

先定义一个类,用来被继承:

function xx(name){
 this.name=name;
}
xx.prototype.eat=function(food){
   console.log(this.name+'正在吃'+food);
};

一。原型链继承

function Cat(){ }
Cat.prototype=new xx();
Cat.prototype.name='cat';
var cat=new Cat();

这种继承方式就是将Cat类的原型指向改变成指向xx类的实例,父类xx新增的原型方法,原型属性,cat都能访问到

二。构造继承(call,apply继承)

function Cat(name){ 
	xx.call(this,name);
}
var cat=new Cat("tom");

这种继承方法的原理是通过把xx类的构造方法在Cat类中调用一次,然后通过call方法让实例cat对象替换xx类的对象来访问xx类的属性和方法,这种方法,显然无法继承xx类原型的属性和方法。

三。拷贝继承

function Cat(name){
	var xx=new xx(name);
	for(var key in xx){
	Cat.prototype[key]=xx[key];
}
}
var cat=new Cat("tom")

这种继承方法比较捞,它的原理是通过构造一个xx的实例对象,然后遍历这个对象,将这个对象上的所有方法属性(当然了,包括原型的)拷贝到Cat类的原型上。

四。组合继承(原型链继承和构造继承的组合)

function Cat(name){
	xx.call(this,name);
}
Cat.prototype=new xx();
Cat.prototype.constructor=Cat;(这句主要是为了修复原型链)
var cat=new Cat("tom");

这种继承方法既可以自己在构造对象时传参,也继承下了父类原型的方法和属性,唯一的缺点是调用了两次父类构造函数,第一次调用只获取了父类的构造函数上的属性和方法,第二次不仅获得了构造函数的属性方法,也获得了原型的,所以构造函数的属性方法重复了一遍。

五。寄生组合继承

function Cat(name){
	xx.call(this,name);
}
(function(){
	//创建一个没有任何方法属性的类
	var yy=function(){ }
	//将xx类的原型的属性方法给yy类的原型
	yy.prototype=xx.prototype;
	//将yy类的实例做为Cat类的原型
	Cat.prototype=new yy();	
})();//函数立即调用

//上面的一系列操作,都是为了把xx类原型的属性方法拿出来,然后给Cat类的原型,这样加上Cat构造函数得到的xx类构造函数的属性和方法,就圆满了,且不会出现重复

六。ES6继承(语法糖)

class xx{
	constructor(name){this.name=name;}
	say(){....}
	eat(){...}
}
class Cat extends xx{
	constructor(name){
	super(name);
	}
}
var tom=new Cat("tom");

其中 constructor 方法是类的构造函数,是一个默认方法,通过 new 命令创建对象实例时,自动调用该方法。一个类必须有 constructor 方法,如果没有显式定义,一个默认的 consructor 方法会被默认添加。所以即使你没有添加构造函数,也是会有一个默认的构造函数的。
一般 constructor 方法返回实例对象 this 通过extends关键字来继承xx类,但是在 constructor 中必须调用 super 方法,因为子类没有自己的 this 对象,而是继承父类的 this 对象,然后对其进行加工,而 super 就代表了父类的构造函数。super 虽然代表了父类 A 的构造函数,但是返回的是子类 B 的实例,即 super 内部的 this 指的是 B,因此 super() 在这里相当于A.prototype.constructor.call(this, props)。
A.prototype就指出了super是等同于父类的原型,constructor.call(this,props)就指出了super返回的是子类B的实例,结合call方法来看,this值当前类实例,也就是B的实例,它代替A的实例来调用constructor方法,而constructor这个方法就是返回实例对象this的,所以返回的是B的实例this。

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值