先看咱们以前在借用构造函数继承中最后用到的代码:函数
//父类:人 function Person () { this.head = '脑壳瓜子'; this.emotion = ['喜', '怒', '哀', '乐']; //人都有喜怒哀乐 this.eat = function () { console.log('吃吃喝喝'); } this.sleep = function () { console.log('睡觉'); } this.run = function () { console.log('快跑'); } } //子类:学生,继承了“人”这个类 function Student(studentID) { this.studentID = studentID; Person.call(this); } //Student.prototype = new Person(); var stu1 = new Student(1001); console.log(stu1.emotion); //['喜', '怒', '哀', '乐'] stu1.emotion.push('愁'); console.log(stu1.emotion); //["喜", "怒", "哀", "乐", "愁"] var stu2 = new Student(1002); console.log(stu2.emotion); //["喜", "怒", "哀", "乐"]
在这段代码中,咱们经过借用构造函数继承,保证了 stu1 和 stu2 都有各自的父类属性副本,从而使得各自 emotion 互不影响。但同时带来的问题是,stu1 和 stu2 都拷贝了 Person 类中的全部属性和方法,而在 Person 类中,像 eat ( ), sleep ( ), run ( ) 这类方法应该是公用的,而不须要添加到每一个实例上去,增大内存,尤为是这类方法较多的时候。this
因此咱们想到,是否能把这些方法挂载到父类的原型对象上去,实现方法复用,而后子类经过原型链继承,就能调用这些方法啦?~spa
//父类:人 function Person () { this.head = '脑壳瓜子'; this.emotion = ['喜', '怒', '哀', '乐']; //人都有喜怒哀乐 } //将 Person 类中需共享的方法放到 prototype 中,实现复用 Person.prototype.eat = function () { console.log('吃吃喝喝'); } Person.prototype.sleep = function () { console.log('睡觉'); } Person.prototype.run = function () { console.log('快跑'); } //子类:学生,继承了“人”这个类 function Student(studentID) { this.studentID = studentID; Person.call(this); } Student.prototype = new Person(); //此时 Student.prototype 中的 constructor 被重写了,会致使 stu1.constructor === Person Student.prototype.constructor = Student; //将 Student 原型对象的 constructor 指针从新指向 Student 自己 var stu1 = new Student(1001); console.log(stu1.emotion); //['喜', '怒', '哀', '乐'] stu1.emotion.push('愁'); console.log(stu1.emotion); //["喜", "怒", "哀", "乐", "愁"] var stu2 = new Student(1002); console.log(stu2.emotion); //["喜", "怒", "哀", "乐"] stu1.eat(); //吃吃喝喝 stu2.run(); //快跑 console.log(stu1.constructor); //Student
首先,咱们将 Person 类中须要复用的方法提取到 Person.prototype 中,而后设置 Student 的原型对象为 Person 类的一个实例,这样 stu1 就能访问到 Person 原型对象上的属性和方法了。其次,为保证 stu1 和 stu2 拥有各自的父类属性副本,咱们在 Student 构造函数中,仍是使用了 Person.call ( this ) 方法。如此,结合原型链继承和借用构造函数继承,就完美地解决了以前这两者各自表现出来的缺点。prototype