手机版

阿里巴巴技术文章分享Javascript继承机制的实现

时间:2021-09-18 来源:互联网 编辑:宝哥软件园 浏览:

作为一种脚本语言,Javascript在设计之初并没有考虑面向对象的特性。即使在现代浏览器时代的今天,各种各样的Javascript框架/库也如雨后春笋般涌现,Javascript中甚至连一个class关键字都没有。如果你想写一个类,你必须使用函数。至于继承和重载,就不要指望了。

然而,没有遗产我们怎么生活?你是否复制了所有的公共逻辑来实现最低级别的代码重用?

答案当然是——NO。所以,一定要自己继承!

目标

当然,关键目标是继承自动拥有父类的——子类的所有公共属性和方法。

支持Instanceof,例如c是子类的实例,P是父类,所以c instanceof P应该返回true。

其次,它应该能够Override父类的方法,在子类的方法中,它可以很容易地转移到父类同名的方法中。

至于Overload,由于Javascript的语言特性,无法实现(不允许同名的方法,即使它们的参数列表不同)。

设计和实施

Javascript对象有一个非常重要的属性——__proto__,这就是原型。原型本质上也是一个对象,所以也可以有自己的原型,从而形成原型链。当您调用对象的方法或读取对象的属性时,Javascript执行器会执行以下操作:

1.首先,在Object中找到对应的方法或属性。如果找不到,2。看物体的原型。如果找不到,3。看原型的原型。四.5.直到最终找到物体的原型。如果没有,返回undefined,如下图所示:

原型链的这个特性类似于继承,所以自然可以用它来实现继承机制。原型链支持instanceof,这是一个不错的选择。

我们定义了extend函数,它接受两个参数,第一个是父类,第二个是子类,如下所示:

函数扩展(ParentClass,ChildClass){ 0.返回ChildClass}此函数处理子类并返回子类。处理逻辑如下:

建立原型链。

通过连接子类的原型链和父类的原型链,子类可以自动拥有父类的方法和属性:

var pp=ParentClass.prototype,cp=ChildClass.prototype函数T(){ };t .原型=ppchild class . prototype=new T();为了连接原型链,需要创建父类的实例,并将其分配给子类的原型属性。但是我们不想在extend方法中实例化父类,所以我们引入了一个中间类t来解决这个问题。

实现重写。

在原型链建立之后,我们还需要保留原始子类原型上的方法和属性:

方法

如果父类有一个同名的方法,我们使用闭包来保存对父类方法和子类方法的引用。然后,在新原型中修改该方法的引用,并将其指向一个新函数。在这个函数中,我们创建一个临时属性super,将其指向父方法,并调用子类方法,这样在子类方法中,可以通过这个调用父方法。

child class . prototype[name]=(function(pm,cm){ return function(){ var _ super=this . super;this.super=pmvar result=cm.apply(这个,参数);this.super=_ super返回结果;};})(pp[name],CP[name]);属性

对于属性,不存在重写问题,因此直接将子类的原始原型中的属性添加到新原型中:

child CLaSS . prototype[name]=CP[name];构造器

为了让子类访问父类的构造函数,我们将父类分配给子类的超级属性:

child CLaSS . super=parent CLaSS;如何使用

假设我们要设计一个管理系统,它涉及客户、工人和管理者。通过抽象客户和员工之间的共性,我们得到了人。然后抽象出员工和管理者之间的共性,得到员工。这样,我们得到了一个三级的类结构:

实现这个设计的代码如下:

函数人们(名,姓){这个。名字=名字;这个。姓氏=姓氏;}函数员工(名字、姓氏、公司){ Employee.super.apply(这个,参数);这家公司=公司;}函数经理(名字、姓氏、公司、头衔){ Manager.super.apply(这个,参数);this.title我们希望对每个人都有一个描述,人们是姓名;员工在姓名之后,还包括公司名称;而经理在员工的描述之后,还包括职位。代码如下:

人们。原型。summary=function(){返回这个。名字叫“这个”。姓氏;};员工。原型。summary=function(){返回这个。超级棒。调用(this)',' this.company };经理。原型。summary=function(){返回这个。超级棒。调用(this)',' this . title };在所有的成员方法都已经定义好之后,声明类的继承(必须先定义方法,再声明类的继承,否则无法在方法中使用这太棒了调用父类方法!):

扩展(人员、员工);扩展(员工、经理);使用这些类就比较简单,直接新的就好了:

var people=new People(《爱丽丝》,《狄更斯》);定义变量员工=新员工(“鲍勃”“雷”阿里巴巴');定义变量经理=新经理('卡尔文''克莱恩''阿里巴巴''高级经理');控制台。日志(人。summary());//Alice dickensonsole。日志(员工。summary());//Bob Ray,alibabaconsole。日志(经理。summary());//阿里巴巴高级经理卡尔文克莱因这篇文章不错吧,那就给个赞吧!

版权声明:阿里巴巴技术文章分享Javascript继承机制的实现是由宝哥软件园云端程序自动收集整理而来。如果本文侵犯了你的权益,请联系本站底部QQ或者邮箱删除。