免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
最近访问板块 发新帖
查看: 976 | 回复: 0
打印 上一主题 下一主题

javascript的prototype继承 [复制链接]

论坛徽章:
0
跳转到指定楼层
1 [收藏(0)] [报告]
发表于 2008-05-02 13:34 |只看该作者 |倒序浏览

                                                                        基本的用法 把ClassA的一个实例赋值给ClassB ClassB就继承了ClassA的所有属性

script>

function ClassA()



{

    this.a='a';

}

function ClassB()



{

    this.b='b';

}

ClassB.prototype=new ClassA();

var objB=new ClassB();

for(var p in objB)document.write(p+"
");

script>
从原型继承理论的角度去考虑 js的原型继承是引用原型 不是复制原型
所以 修改原型会导致所有B的实例的变化

script>

function ClassA()



{

    this.a='a';

}

function ClassB()



{

    this.b='b';

}

ClassB.prototype=new ClassA();

var objB=new ClassB();

alert(objB.a);

ClassB.prototype.a='changed!!';

alert(objB.a);

script>
然而 子类对象的写操作只访问子类对象中成员 它们之间不会互相影响
因此 写是写子类 读是读原型(如果子类中没有的话)

script>

function ClassA()



{

    this.a='a';

}

function ClassB()



{

    this.b='b';

}

ClassB.prototype=new ClassA();

var objB1=new ClassB();

var objB2=new ClassB();

objB1.a='!!!';

alert(objB1.a);

alert(objB2.a);

script>
每个子类对象都执有同一个原型的引用 所以子类对象中的原型成员实际是同一个

script>

function ClassA()



{


    this.a=function()

{alert();};

}

function ClassB()



{


    this.b=function()

{alert();};

}

ClassB.prototype=new ClassA();

var objB1=new ClassB();

var objB2=new ClassB();

alert(objB1.a==objB2.a);

alert(objB1.b==objB2.b);

script>
构造子类时 原型的构造函数不会被执行

script>

function ClassA()



{

    alert("a");


    this.a=function()

{alert();};

}

function ClassB()



{

    alert("b");


    this.b=function()

{alert();};

}

ClassB.prototype=new ClassA();

var objB1=new ClassB();

var objB2=new ClassB();

script>
接下来是致命的,在子类对象中访问原型的成员对象:

script>

function ClassA()



{

    this.a=[];

}

function ClassB()



{


    this.b=function()

{alert();};

}

ClassB.prototype=new ClassA();

var objB1=new ClassB();

var objB2=new ClassB();

objB1.a.push(1,2,3);

alert(objB2.a);

//所有b的实例中的a成员全都变了!!

script>
所以 在prototype继承中 原型类中不能有成员对象! 所有成员必须是值类型数据(string也可以)
用prototype继承有执行效率高,不会浪费内存,为父类动态添置方法后子类中马上可见等的优点。
prototype继承是通过把子类的原型对象(prototype)设置成父类的一个实例来进行继承的。
有不少缺点。总的来说有四个缺点:
  缺点一:父类的构造函数不是像JAVA中那样在给子类进行实例化时执行的,而是在设置继承的时候执行的,并且只执行一次。这往往不是我们希望的,特别是父类的构造函数中有一些特殊操作的情况下。
 
 缺点二:由于父类的构造函数不是在子类进行实例化时执行,在父类的构造函数中设置的成员变量到了子类中就成了所有实例对象公有的公共变量。由于
JavaScript中继承只发生在“获取”属性的值时,对于属性的值是String,Number和Boolean这些数据本身不能被修改的类型时没有
什么影响。但是Array和Object类型就会有问题。
  缺点三:如果父类的构造函数需要参数,我们就没有办法了。
  缺点四:子类原本的原型对象被替换了,子类本身的constructor属性就没有了。在类的实例取它的constructor属性时,取得的是从父类中继承的constructor属性,从而constructor的值是父类而不是子类。
我也曾经为了这四个缺点头疼过,于是对prototype继承进行改造。
我试了几种方法,下面是我觉得最好的一种。我把它写成Function对象的一个方法,这样用的时候方便。方法如下:

//类的继承-海浪版

Function.prototype.Extends = function (parentClass)



{

  var Bs = new Function();

  Bs.prototype = parentClass.prototype;

  this.prototype = new Bs();

  this.prototype.Super = parentClass;

  this.prototype.constructor = this;

}
               
               
               
               
               
               
               
               
               
               
               

本文来自ChinaUnix博客,如果查看原文请点:http://blog.chinaunix.net/u2/68052/showart_654855.html
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP