JavaScript高级程序设计 阅读笔记(十四) js继承机制的实现

继承

  继承是面向对象语言的必备特征,即一个类能够重用另一个类的方法和属性。在JavaScript中继承方式的实现方式主要有以下五种:对象冒充、call()、apply()、原型链、混合方式。

  下面分别介绍。

对象冒充

  原理:构造函数使用this关键字给所有属性和方法赋值。因为构造函数只是一个函数,所以可以使ClassA的构造函数成为ClassB的方法,然后调用它。ClassB就会收到ClassA的构造函数中定义的属性和方法。

  示例:


代码如下:

function ClassA(sColor){
this.color=sColor;
this.sayColor=function(){
alert(this.color);
}
}

function ClassB(sColor,sName){
this.newMethod=ClassA;
this.newMethod(sColor);
delete this.newMethod;

this.name=sName;
this.sayName=function(){
alert(this.name);
}
}

调用:


代码如下:

var objb=new ClassB("blue","Test");
objb.sayColor();//
blueobjb.sayName(); // Test  

注意:这里要删除对ClassA的引用,否则在后面定义新的方法和属性会覆盖超类的相关属性和方法。用这种方式可以实现多重继承。

call()方法

  由于对象冒充方法的流行,在ECMAScript的第三版对Function对象加入了两个新方法 call()和apply()方法来实现相似功能。

  call()方法的第一个参数用作this的对象,其他参数都直接传递给函数自身。示例:


代码如下:

function sayColor(sPrefix,sSuffix){
alert(sPrefix+this.color+sSuffix);
}

var obj=new Object();
obj.color="red";

//output The color is red, a very nice color indeed.
sayColor.call(obj,"The color is ",", a very nice color indeed.");

 使用此方法来实现继承,只需要将前三行的赋值、调用、删除代码替换即可:


代码如下:

function ClassB(sColor,sName){
//this.newMethod=ClassA;
//this.newMethod(sColor);
//delete this.newMethod;
ClassA.call(this,sColor);

this.name=sName;
this.sayName=function(){
alert(this.name);
}
}

apply()方法

  apply()方法跟call()方法类似,不同的是第二个参数,在apply()方法中传递的是一个数组。


代码如下:

function sayColor(sPrefix,sSuffix){
alert(sPrefix+this.color+sSuffix);
}

var obj=new Object();
obj.color="red";

//output The color is red, a very nice color indeed.
sayColor.apply(obj,new Array("The color is ",", a very nice color indeed."));

使用此方法来实现继承,只需要将前三行的赋值、调用、删除代码替换即可:


代码如下:

function ClassB(sColor,sName){
//this.newMethod=ClassA;
//this.newMethod(sColor);
//delete this.newMethod;
ClassA.apply(this,new Array(sColor));

this.name=sName;
this.sayName=function(){
alert(this.name);
}
}

跟call()有一点不同的是,如果超类中的参数顺序与子类中的参数顺序完全一致,第二个参数可以用arguments。

原型链

  继承这种形式在ECMAScript中原本是用于原型链的。Prototype对象的任何属性和方法都被传递给那个类的所有实例。原型链利用这种功能实现继承机制。

  用原型链实现继承示例:


代码如下:

function ClassA(){
}

ClassA.prototype.color="red";
ClassA.prototype.sayColor=function(){
alert(this.color);
};

function ClassB(){
}

ClassB.prototype=new ClassA();

 注意:调用ClassA的构造函数时,没有给它传递参数。这在原型链中是标准的做法,要确保构造函数没有任何参数。

混合方式

  这种方式混合了对象冒充和原型链方式。示例:


代码如下:

function ClassA(sColor){
this.color=sColor;
}
ClassA.prototype.sayColor=function(){
alert(this.color);
}

function ClassB(sColor,sName){
ClassA.call(this,sColor);
this.name=sName;
}

ClassB.prototype=new ClassA();
ClassB.prototype.sayName=function(){
alert(this.name);
}

调用示例:


代码如下:

var objb=new ClassB("red","test");
objb.sayColor();// output red
objb.sayName();// output test

作者:Artwl

(0)

相关推荐

  • 基于JavaScript实现继承机制之构造函数方法对象冒充的使用详解

    继承的方式 ECMAScript 实现继承的方式不止一种.这是因为 JavaScript 中的继承机制并不是明确规定的,而是通过模仿实现的.这意味着所有的继承细节并非完全由解释程序处理.作为开发者,你有权决定最适用的继承方式.最原始的继承实现方式就是对象冒充,下面着重介绍该方法. 对象冒充 对象冒充实现继承的核心其实依赖于在函数环境中使用 this 关键字.其原理如下:构造函数使用 this 关键字给所有属性和方法赋值(即采用类声明的构造函数方式).因为构造函数只是一个函数,所以可使 Class

  • 由JavaScript中call()方法引发的对面向对象继承机制call的思考

    起因: 今天在阅读snandy大神的读jQuery之五(取DOM元素)时,看到有讲到toArray()方法,具体jQuery代码如下: 复制代码 代码如下: toArray: function() { return slice.call( this, 0 ); }, get: function( num ) { return num == null ? // Return a 'clean' array this.toArray() : // Return just the object ( n

  • JavaScript 继承机制的实现(待续)

    1.对象冒充 原理:构造函数使用this关键字给所有属性和方法赋值(即采用类声明的构造函数方式). 因为构造函数只是一个函数,所以可使ClassA的构造函数成为ClassB的方法,然后调用它.ClassB就会收到ClassA的构造函数中定义的属性和方法. 例如: 下面方式定义的ClassA和ClassB: 复制代码 代码如下: function ClassA(sColor){ this.color=sColor; this.sayColor=function(){ alert(this.colo

  • Javascript 继承机制的实现

    选定基类后,就可以创建它的子类了.是否使用基类完全由你决定.有时,你可能想创建一个不能直接使用的基类,它只是用于给子类提供通用的函数.在这种情况下,基类被看作抽象类. 尽管ECMAScript并没有像其他语言那样严格地定义抽象类,但有时它的确会创建一些不允许使用的类.通常,我们称这种类为抽象类. 创建的子类将继承超类的所有属性和方法,包括构造函数及方法的实现.记住,所有属性和方法都是公用的,因此子类可直接访问这些方法.子类还可添加超类中没有的新属性和方法,也可以覆盖超类中的属性和方法. 4.2.

  • JavaScript不使用prototype和new实现继承机制

    此方法并非笔者原创,笔者只是在前辈的基础上,加以总结,得出一种简洁实用的JavaScript继承方法. 传统的JavaScript继承基于prototype原型链,并且需要使用大量的new操作,代码不够简洁,可读性也不是很强,貌似还容易受到原型链污染. 笔者总结的继承方式,简洁明了,虽然不是最好的方式,但希望能给读者带来启发. 好了,废话不多说,直接看代码,注释详尽,一看就懂~~~ 复制代码 代码如下: /**   * Created by 杨元 on 14-11-11.   * 不使用prot

  • javascript继承机制实例详解

    本文实例讲述了javascript继承机制.分享给大家供大家参考.具体分析如下: 初学javascript一般很难理解Javascript语言的继承机制它没有"子类"和"父类"的概念,也没有"类"(class)和"实例"(instance)的区分,全靠一种很奇特的"原型链"(prototype chain)模式,来实现继承. 我花了很多时间,学习这个部分,还做了很多笔记.但是都属于强行记忆,无法从根本上理解

  • javascript类继承机制的原理分析

    目前 javascript的实现继承方式并不是通过"extend"关键字来实现的,而是通过 constructor function和prototype属性来实现继承.首先我们创建一个animal 类 js 代码 复制代码 代码如下: var animal = function (){ //这就是constructor function 了 this .name = 'pipi'; this .age = 10; this .height = 0; } //建立一个动物的实例 var

  • Javascript继承机制的设计思想分享

    我一直很难理解Javascript语言的继承机制. 它没有"子类"和"父类"的概念,也没有"类"(class)和"实例"(instance)的区分,全靠一种很奇特的"原型链"(prototype chain)模式,来实现继承. 我花了很多时间,学习这个部分,还做了很多笔记.但是都属于强行记忆,无法从根本上理解. 直到昨天,我读到法国程序员Vjeux的解释,才恍然大悟,完全明白了Javascript为什么这样

  • 基于JavaScript实现继承机制之原型链(prototype chaining)的详解

    如果用原型方式重定义前面例子中的类,它们将变为下列形式: 复制代码 代码如下: function ClassA() {} ClassA.prototype.color = "blue";ClassA.prototype.sayColor = function () {    alert(this.color);}; function ClassB() {} ClassB.prototype = new ClassA(); 原型方式的神奇之处在于最后一行代码.这里,把 ClassB 的

  • Javascript 继承机制实例

    实际上,几何形状只有两种,即椭圆形(是圆形的)和多边形(具有一定数量的边).圆是椭圆形的一种,它只有一个焦点.三角形.矩形和五边形都是多边形的一种,具有不同数量的边.正方形是矩形的一种,所有的边等长.这就构成了一种完美的继承关系. 在这个例子中,形状(Shape)是椭圆形(Ellipse)和多边形(Polygon)的基类(base class)(所有类都由它继承而来).椭圆具有一个属性foci,说明椭圆具有的焦点的个数.圆形(Circle)继承了椭圆形,因此圆形是椭圆形的子类(subclass)

  • 基于JavaScript实现继承机制之调用call()与apply()的方法详解

    call() 方法call() 方法是与经典的对象冒充方法最相似的方法.它的第一个参数用作 this 的对象.其他参数都直接传递给函数自身.例如: 复制代码 代码如下: function sayHello(sPrefix,sSuffix) {    alert(this.name + "says" + sPrefix + sSuffix);}; var obj = new Object();obj.name = "Tom"; sayHello.call(obj, &

  • 基于JavaScript实现继承机制之构造函数+原型链混合方式的使用详解

    构造函数.原型实现继承的缺陷 首先来分析构造函数和原型链两种实现继承方式的缺陷: 构造函数(对象冒充)的主要问题是必须使用构造函数方式,且无法继承通过原型定义的方法,这不是最好的选择.不过如果使用原型链,就无法使用带参数的构造函数了.开发者如何选择呢?答案很简单,两者都用. 构造函数+原型混合方式 这种继承方式使用构造函数定义类,并非使用任何原型.创建类的最好方式是用构造函数定义属性,用原型定义方法.这种方式同样适用于继承机制,用对象冒充继承构造函数的属性,用原型链继承 prototype 对象

随机推荐