导读:
今天要讨论的主题是下面3种方案的对比:
前提:
代码
var m1 = function(){}; var m2 = function(){};
要对比的3种方案是:
代码
1>Object.extend( m1.prototype, m2.prototype );2>m1.prototype = m2.prototype;3>m1.prototype = new m2();
下面对各种方案先预先给予说明:
1>第一种方案是将m2.prototype该对象中所有成员拷贝(覆盖)到m1.prototype对象中。
看代码:
代码
var m1 = function(){}; var m2 = function(){}; var o2 = new m2(); o2.name = 'qk'; m2.prototype.print = function(){ alert( this.name );} Object.extend( m1.prototype, m2.prototype );
到此,我们可以想象,m2.prototype中的成员变量print已经拷贝到m1.prototype中,即,凡m1对象便拥有print成员。假如我们试图创建m1的对象,
代码
var o1 = new m1();
则我们可以调用o1.print();但由于m1对象中不存在name属性,故会是undefined。问题在哪?是因为m2.prototype对象的成员中包含了m2的实例变量name,这种设计方案是不合理的(这里只是为了演示所用,现实中是不会出现类似的代码的,下同)。
2>第二种方案是将m1.prototype对象的指针指向m2.prototype的内存地址。或m1.prototype对象只是m2.prototype对象的一个引用。试图改变m2.prototype内存地址后不会影响m1.prototype对象成员的变化。看代码:
代码
var m1 = function(){}; var m2 = function(){}; var o2 = new m2(); o2.name = 'qk'; m2.prototype.print = function(){ alert( this.name );} m1.prototype = m2.prototype;// 改变m2.prototype m2.prototype = {0:0};// 打印 var o1 = new m1(); for( var key in o1 ){ alert( key + '=>' + o1[ key ] );}
不过,如果对m2.prototype对象的成员进行增加或删除,m1.prototype就会改变。看代码:
代码
var m1 = function(){}; var m2 = function(){}; var o2 = new m2(); o2.name = 'qk'; m2.prototype.print = function(){ alert( this.name );} m1.prototype = m2.prototype;// 增加m2.prototype对象的成员。 m2.prototype[0] = 0;// 打印 var o1 = new m1(); for( var key in o1 ){ alert( key + '=>' + o1[ key ] );}
3>第二种方案是让m1.prototype链式继承m2.prototype的所有成员。即m1.prototype继承m2.prototype,m2.prototype继承Object.prototype.它于第二种方案的不同是,第二种方案中,m1.prototype只是m2.prototype对象的一个引用。只有增加或删除m2.prototype成员才会引起m1.prototype成员的变化。它于第一种方案的不同是,第一种方案中,m1.prototype成员只会增加,不会减少。而这里是链式继承。看代码:
代码
var m1 = function(){}; var m2 = function(){}; var o2 = new m2(); o2.name = 'qk'; m2.prototype.print = function(){ alert( this.name );} m1.prototype = new m2();// 打印 var o1 = new m1(); for( var key in o1 ){ alert( key + '=>' + o1[ key ] );}
此时,o1对象访问属性的顺序是:
m1.prototype对象成员 >m2的实例变量 >m2.prototype对象成员 >m1的的实例变量
好了,介绍完这3种“继承”后,希望大家对javascript的prototype的继承有了更深一步的了解!
本文转自
http://j2eeqk.javaeye.com/blog/70028
今天要讨论的主题是下面3种方案的对比:
前提:
代码
var m1 = function(){}; var m2 = function(){};
要对比的3种方案是:
代码
1>Object.extend( m1.prototype, m2.prototype );2>m1.prototype = m2.prototype;3>m1.prototype = new m2();
下面对各种方案先预先给予说明:
1>第一种方案是将m2.prototype该对象中所有成员拷贝(覆盖)到m1.prototype对象中。
看代码:
代码
var m1 = function(){}; var m2 = function(){}; var o2 = new m2(); o2.name = 'qk'; m2.prototype.print = function(){ alert( this.name );} Object.extend( m1.prototype, m2.prototype );
到此,我们可以想象,m2.prototype中的成员变量print已经拷贝到m1.prototype中,即,凡m1对象便拥有print成员。假如我们试图创建m1的对象,
代码
var o1 = new m1();
则我们可以调用o1.print();但由于m1对象中不存在name属性,故会是undefined。问题在哪?是因为m2.prototype对象的成员中包含了m2的实例变量name,这种设计方案是不合理的(这里只是为了演示所用,现实中是不会出现类似的代码的,下同)。
2>第二种方案是将m1.prototype对象的指针指向m2.prototype的内存地址。或m1.prototype对象只是m2.prototype对象的一个引用。试图改变m2.prototype内存地址后不会影响m1.prototype对象成员的变化。看代码:
代码
var m1 = function(){}; var m2 = function(){}; var o2 = new m2(); o2.name = 'qk'; m2.prototype.print = function(){ alert( this.name );} m1.prototype = m2.prototype;// 改变m2.prototype m2.prototype = {0:0};// 打印 var o1 = new m1(); for( var key in o1 ){ alert( key + '=>' + o1[ key ] );}
不过,如果对m2.prototype对象的成员进行增加或删除,m1.prototype就会改变。看代码:
代码
var m1 = function(){}; var m2 = function(){}; var o2 = new m2(); o2.name = 'qk'; m2.prototype.print = function(){ alert( this.name );} m1.prototype = m2.prototype;// 增加m2.prototype对象的成员。 m2.prototype[0] = 0;// 打印 var o1 = new m1(); for( var key in o1 ){ alert( key + '=>' + o1[ key ] );}
3>第二种方案是让m1.prototype链式继承m2.prototype的所有成员。即m1.prototype继承m2.prototype,m2.prototype继承Object.prototype.它于第二种方案的不同是,第二种方案中,m1.prototype只是m2.prototype对象的一个引用。只有增加或删除m2.prototype成员才会引起m1.prototype成员的变化。它于第一种方案的不同是,第一种方案中,m1.prototype成员只会增加,不会减少。而这里是链式继承。看代码:
代码
var m1 = function(){}; var m2 = function(){}; var o2 = new m2(); o2.name = 'qk'; m2.prototype.print = function(){ alert( this.name );} m1.prototype = new m2();// 打印 var o1 = new m1(); for( var key in o1 ){ alert( key + '=>' + o1[ key ] );}
此时,o1对象访问属性的顺序是:
m1.prototype对象成员 >m2的实例变量 >m2.prototype对象成员 >m1的的实例变量
好了,介绍完这3种“继承”后,希望大家对javascript的prototype的继承有了更深一步的了解!
本文转自
http://j2eeqk.javaeye.com/blog/70028