本文是原创文章,如需转载,请注明文章出处
1.js中实现组合继承(B继承A):
function A(name){ this.name = name; this.ary = ["AA","BB","CC"]; } A.prototype.say = function() { console.log(this.name); console.log(this.ary); } function B(name, age){ A.call(this, name); //第二次调用 this.age = age; } B.prototype = new A(); //第一次调用 B.prototype.constructor = B;
function main(){
var b = new B("Nick", 30);
b.say();
}
这种继承方式主要是利用原型链实现继承,同时使用构造函数传入参数,每当生成B对象时,会调用A的构造函数添加name和ary属性从而实现继承。
但这种方式有个缺陷,会调用2次A的构造函数,第一次是在设置prototype时,此时B.prototype指向一个A的实例,实例中保存着一份name和ary;第二次是在生成B对象时,B的构造函数会调用A的构造函数,在B对象中添加name和ary属性,当访问B对象属性时,发现B对象中有name和ary,所以返回的值是我们所期望的。
2.寄生组合式继承(B继承A):
function inherit(B, A){ var prototype = object(A.prototype); B.prototype = prototype; prototype.constructor = B; } function object(o){ function F(){}; F.prototype = o; return new F(); } function A(name){ this.name = name; this.ary = ["AA", "BB", "CC"]; } A.prototype.sayName = function() { console.log(this.name); } function B(name, age){ A.call(this, name); this.age = age; } inherit(B, A); B.prototype.sayAge = function() { console.log(this.age); } function main(){ var instance = new B("Nick", 30); instance.sayName(); //"Nick" instance.sayAge(); //30 }
这种继承方式跟第一种很相似,区别就是使用了inherit方法,首先创建A原型的一个副本,然后将因重写原型而失去的constructor指向B,最后将新创建的原型副本赋值给B的原型。
这种方式的好处就是不会调用两次父超类型的构造函数,不用创建多余属性。