一、创建对象的几种办法
// 1、字面量var o1 = {name:'lihaixing'};var o11 = new Object({name:'lihaixing'});// 2、构造函数var M = function(){this.name='haixing'};var o2 = new M();// 3、基于原型var P = {name:'haixing'};var o3 = Object.create(P);var o33 = Object.create(null);
二、原型链
var M = function () { this.name = 'haixing'; // return {}};var o2 = new M();console.log(M.prototype.constructor === M); // trueconsole.log(M.prototype === o2.__proto__); // trueconsole.log(M.prototype.__proto__ === Object.prototype); // trueconsole.log(M.__proto__ === Function.prototype); // trueconsole.log(Object.prototype.__proto__===null); // trueconsole.log(o2 instanceof M); // true console.log(M.prototype instanceof Object); // true console.log(o2 instanceof Object); // true 只有一条链上就能够
三、继承
1、借助构造函数实现继承
function Parent1 () { this.name = 'parent1' this.play = [1, 2, 3]}function Child1 () { Parent1.call(this) this.type = 'child1'}
毛病:只是将Parents的this指向了Child1的实例,但Parents.prototype中的属性却无奈继承下来
// 测试Parent1.prototype.say=function(){ console.log('Parent1 prototye')}var son1 = new Child1();son1.say(); // Uncaught TypeError: son1.say is not a function
2、借助原型链实现继承
function Parent2 () { this.name = 'parent2' this.play = [1, 2, 3]}function Child2 () { this.type = 'child2'}Child2.prototype = new Parent2();
毛病:尽管实现了继承,然而父类实例后的数据却是共用得,导致某个实例扭转父亲的数据,其它儿子也就共享了
// 测试Parent2.prototype.say = function () { console.log('say')}var son2 = new Child2();var son22 = new Child2();son2.say(); // sayson2.play.push(4);console.log(son22.play); // [ 1, 2, 3, 4 ]
3、联合以上两种办法实现继承
function Parent3 () { this.name = 'parent3' this.play = [1, 2, 3]}function Child3 () { Parent3.call(this) this.type = 'child3'}Child3.prototype = new Parent3()
毛病:尽管解决了各自的毛病,但父类执行了两次,并且父类和子类还有雷同的属性
4、父类的原型赋值给子类
function Parent4 () { this.name = 'parent4' this.play = [1, 2, 3]}function Child4 () { Parent4.call(this) this.type = 'child3'}Child4.prototype = Parent4.prototype
毛病:
- Child4.prototype = Parent4.prototype 使得Child4和Parent4实例得结构器都指向了Parent4, 这显著不是咱们想要的,咱们心愿Child4.prototype.contructor依然是Child4
- 有人想到Child4.prototype.constructor = Child4将结构器再改回来,然而这样Parent4.prototype.contructor成了Child4也不妥呀
// 测试var son4 = new Child4();// instanceof 取决于由谁创立的,同一条线都可console.log(son4 instanceof Child4, son4 instanceof Parent4) // true true// 结构器在原型上呢,取决于Child4.prototype.contructorconsole.log(Child4.prototype.constructor, Parent4.prototype.constructor) // Parent4 Parent4
5、基于object.create
function Parent5 () { this.name = 'parent5' this.play = [1, 2, 3]}function Child5 () { Parent5.call(this) this.type = 'child5'}Child5.prototype = Object.create(Parent5.prototype);Child5.prototype.constructor = Child5;
最初一个比拟完满,不说了
var son5 = new Child5();console.log(son5 instanceof Child5, son5 instanceof Parent5); // true trueconsole.log(Child5.prototype.constructor,Parent5.prototype.constructor); // Child5 Parent5