复习一下js 的继承相关的知识~~
许多面向对象 语言都支持两种继承方式,接口继承和实现继承。 接口继承只继承方法签名,而实现继承则继承实现的方法。而由于函数没有签名,在ECMAScript 中无法实现接口继承。ECMAScript 只支持实现继承, 而且其实现继承主要是依靠原型链来实现的。
场景: 创建子类Child, 继承父类People的方法,并调用say函数说出姓名和年龄
function People(name, age) {
this.name = name;
this.age = age;
this.say = function() {
console.log("我的名字是:" + this.name + "我今年" + this.age + "岁了!");
}
}
ECMAScript 中描述了原型链的概念,并将原型链作为实现继承的主要方法。其主要思想是利用原型让一个引用类型继承另一个引用类型的属性和方法。
function Child(name, age) {
this.name = name;
this.age = age;
}
Child.prototype = new People();
var child = new Child('Lorin', 22);
child.say();
基本思想:在子类型构造函数的内部调用超类型构造函数。
function Child(name, age) {
People.call(this);
this.name = name;
this.age = age;
}
var child = new Child('Lorin', 22);
child.say();
组合继承有时候也叫做伪经典继承,指的是将原型链和借用构造函数的技术组合到一起,从而发挥二者之长的一种继承模式。其背后的思想是使用原型链实现对原型属性和方法的继承,而通过借用构造函数来实现对实例属性的继承。这样既通过在原型上定义方法实现了函数的复用,又能保证每个实例都有它自己的属性。
组合继承式js最常用的继承模式。
function Child(name, age) {
People.call(this); //借用了构造函数继承模式
this.name = name;
this.age = age;
}
Child.prototype = People.prototype; //原型链继承
var child = new Child('Lorin', 22);
child.say();
是由道格拉斯.克罗克服德在2006年写了一篇文章,介绍的一种实现继承的方法,这种方法并没有使用
严格意义上的构造函数。他的想法是借助原型可以基于已有的对象创建新对象,同时还不必因此创建自定义类型。
为达到该目睹,他给出了如下函数:
function object(o) {
function F();
F.prototype = o;
return new F();
}
在object() 函数内部,先创建了一个临时性的构造函数,然后将传入的对象作为这个构造函数的原型。最后返回了这个临时类型的一个新实例,从本质上讲,object() 对传入的对象执行了一次浅复制。
ECMAScript 5通过新增object.create() 方法规范化了原型式继承。这个方法接收两个参数: 一个用作新对象
原型的对象和(可选的)一个新对象定义额外属性的对象。在传入一个参数的情况下,
Object.create()与 object()方法的行为相同。
寄生式继承是与原型式继承紧密相关的一种思路,并且同样也是克罗克罗克福德推而广之的。寄生式继承的思路与寄生构造函数和工厂模式类似,即创建一个仅用于封装继承过程的函数,该函数在内部以某种方式来增强对象,最后再像真地是它做了所有工作一样返回对象。以下代码示范了寄
生式继承模式。
function createAnother(obj) {
var clone = object(original); //通过调用函数创建一个新对象
clone.sayHi = function() { //以某种方式来增强这个对象
console.log('hi');
};
return clone; //返回这个对象
}
组合继承虽然是js最常用的继承模式,不过,它也有不足。组合继承最大的问题是无论什么情况下,都会调用两次超类型构造函数:一次是在创建子类型原型的时候,另一次是在子类型构造函数内部。寄生组合式继承是引用类型最理想的继承方式。
寄生组合式继承的基本模式如下:
function inheriPrototype (subType, superType) {
var prototype = object(superType.prototype); //创建对象
prototype.constructor = subType; //增强对象
subType.prototype = prototype; //指定对象
}
场景题解决:
function Child(name, age) {
People.call(this);
this.name = name;
this.age = age;
}
Child.prototype = Object.create(People.prototype);
Child.prototype.constructor = Child;
var child = new Child('Lorin', 22);
child.say();