深入js的面向对象学习篇(继承篇)——温故知新(三)
写这篇有关继承的文章时,突然想起,几天前的面试。因为习惯在学习知识的时候加上自己的理解,很喜欢用自己话来解释,于是乎当面试被问起继承原理时,噼里啪啦一大堆都是自己组织的话,(也可能是因为个人紧张、外加是电面,各种因素掺杂,导致了表述不清),不管怎么然后面试官就被迷茫了。so sorry~私下里可以用“俚语”解释给自己听,一上场面还是需要“官方官言”的。这也算是一种态度。
依然相信绝大多数东西的存在都是有原因的。~
为什么要继承?
减少重复性的代码,并且尽量弱化对象间的耦合。
类式继承
通过用函数来声明类、用关键字new来创建实例。
首先创建构造函数,其名称就是类名,首字母应大写。在构造函数中,创建实例属性要使用关键字this。
function Person(name) { this.name = name; } Person.prototype.getName = function() { return this.name; }; var reader = new Person("Jsno"); reader.getName(); function Author(name,books) { Person.call(this,name); this.books = books; } Author.prototype = new Person(); //重写原型链 Author.prototype.constructor = Author; Author.prototype.getBooks = function() { return this.books; };
原型式继承
var Person = { //所有创建的其它各种类Person对象的原型对象 name: 'default name', getName: function() { return this.name; } }; var Author = clone(Person); Author.books = []; Author.getBooks = function() { return this.books; } function clone(object) { function F() {} F.prototype = object; return new F; }
类式继承和原型继承的对比:
原型继承更能节约资源。原型链读取成员的方式使得所有克隆出来的对象都共享每个属性和方法的唯一一份实例,只有在直接设置了某个克隆出来的对象的属性和方法时,情况才会有所变化。与此相比,在类似继承方法中创建的每一个对象在内存中都有自己的一套属性(和私用方法)的副本。原型继承在这方面的节约效果突出。这种继承也比类式继承显得更为简练。它只用到了一个clone函数,不像后者那样需要为每一个想扩展的类写上好几行像SuperClass.call(this,arg)和SubClass.prototype = new SuperClass。~原型继承所要注意的一个问题就是,万一不小心修改了原型,则会反映到所有继承了该原型的对象中。