理解JavaScript继承(二)
理解JavaScript继承(二)
5.寄生式继承
function object(o) {
function F() {}
F.prototype = o;
return new F();
}
function createAnother(original){
var clone = object(original);//通过调用函数创建一个新对象
clone.sayHi=function(){//以某种方式增强这个对象
alert("hi");
};
return clone;//返回这个对象
}
var person={
name:"Nicholas",
friends:["Shelby","Court,"Van"]
};
var anotherPerson=createAnother(person);
anotherPerson.sayHi();//"hi"
这个实例基于person返回了一个新对象anotherPerson。新对象不仅具有person的所有属性和方法,而且还有自己的sayHi()方法。
缺点:和构造函数一样,不能做到函数复用而降低效率。
6.寄生组合式继承
前面介绍说组合继承是JavaScript最常用的继承模式;实际上,它也存在一些问题,组合继承的最大问题是无论什么情况下,都会调用两次超类型构造函数:一次是在创建子类型原型的时候,另一次是在子类型构造函数内部。
组合式继承实例
function SuperType(name){
this.name = name;
this.colors = ["red", "blue", "green"];
}
SuperType.prototype.sayName = function(){
alert(this.name);
};
function SubType(name, age){
SuperType.call(this, name);//第二次调用SuperType()
this.age = age;
}
SubType.prototype = new SuperType();//第一次调用SuperType()
SubType.prototype.sayAge = function(){
alert(this.age);
};
在第一次调用SuperType()构造函数时,SubType.prototype会得到两个属性:name和colors;他们都是SuperType的实例属性,只不过现在位于SubType的原型中。当调用SubType构造函数时,又会调用一次SuperType构造函数,这一次又在新对象上创建了实例属性name和colors,于是,这两个属性就屏蔽了原型中的两个同名属性。
上面一共有两组name和colors属性:一组在实例上,一组在SubType原型中。这就是调用两次SuperType的结果。
为了解决这种情况,于是就出现了下面的——寄生组合式继承方法。
所谓寄生组合式继承,即通过借用构造函数来继承属性,通过原型链的混成形式来继承方法。其背后的基本思路是:不必为了指定子类型的原型而调用超类型的构造函数,我们所需要的无非就是超类型原型的一个副本而已。(之所以是超类型的副本,而不是直接是超类型,如果直接是超类型的话。当子类型为原型添加方法时,也会影响到超类型的)
寄生组合式继承
function object(o){
function F(){}
F.prototype = o;
return new F();
}
function inheritPrototype(subType, superType){
var prototype = object(superType.prototype); //创建对象
prototype.constructor = subType; //增强对象
subType.prototype = prototype; //指定对象
}
function SuperType(name){
this.name = name;
this.colors = ["red", "blue", "green"];
}
SuperType.prototype.sayName = function(){
alert(this.name);
};
function SubType(name, age){
SuperType.call(this, name);
this.age = age;
}
inheritPrototype(SubType, SuperType);
SubType.prototype.sayAge = function(){
alert(this.age);
};
var instance1 = new SubType("Nicholas", 29);
instance1.colors.push("black");
alert(instance1.colors); //"red,blue,green,black"
instance1.sayName(); //"Nicholas";
instance1.sayAge(); //29
var instance2 = new SubType("Greg", 27);
alert(instance2.colors); //"red,blue,green"
instance2.sayName(); //"Greg";
instance2.sayAge(); //27
上面实例只在SuperType.call(this, name);这调用了一次构造函数,并且因此避免了在prototype上面创建不必要的,多余的属性。
注:YUI的extend()就是采用这种寄生组合式继承
理解JavaScript继承(二)的更多相关文章
- 理解JavaScript继承
原文:理解JavaScript继承 对于JavaScript的继承和原型链,虽然之前自己看了书也听了session,但还是一直觉得云里雾里,不禁感叹JavaScript真是一门神奇的语言.这次经过Sp ...
- 理解JavaScript继承(三)
理解JavaScript继承(三) 通过把父对象的属性,全部拷贝给子对象,也能实现继承. 7.浅拷贝 function extendCopy(p) { var o = {}; for (var pro ...
- 理解JavaScript继承(一)
理解JavaScript继承(一) 我们都知道,面向对象的编程语言非常强大,之所以强大,就是其支持继承.在JavaScript中,也支持继承,而且有多种方法实现继承,比如原型链继承,借用构造函数继承, ...
- 深入理解 JavaScript(二)
立即调用的函数表达式 前言 大家学 JavaScript 的时候,经常遇到自执行匿名函数的代码,今天我们主要就来想想说一下自执行. 在详细了解这个之前,我们来谈了解一下"自执行"这 ...
- javascript继承(二)—创建对象的三种模式
一.工厂模式 function createPerson(name,age){ var o = {}; o.name = name; o.age = age; o.sayHi = function() ...
- 彻底理解Javascript原型继承
彻底理解Javascript原型继承 之前写过一篇Javascript继承主题的文章,这篇文章作为一篇读书笔记,分析的不够深入. 本文试图进一步思考,争取彻底理解Javascript继承原理 实例成员 ...
- 理解Javascript的动态语言特性
原文:理解Javascript的动态语言特性 理解Javascript的动态语言特性 Javascript是一种解释性语言,而并非编译性,它不能编译成二进制文件. 理解动态执行与闭包的概念 动态执行: ...
- 深入理解javascript原型和闭包(6)——继承
为何用“继承”为标题,而不用“原型链”? 原型链如果解释清楚了很容易理解,不会与常用的java/C#产生混淆.而“继承”确实常用面向对象语言中最基本的概念,但是java中的继承与javascript中 ...
- 理解JavaScript中的原型继承(2)
两年前在我学习JavaScript的时候我就写过两篇关于原型继承的博客: 理解JavaScript中原型继承 JavaScript中的原型继承 这两篇博客讲的都是原型的使用,其中一篇还有我学习时的错误 ...
随机推荐
- Linux:网络工具 nc
虽然叫nc不过用起来非常方便. 选项 - Use IPv4 only - Use IPv6 only -U, --unixsock Use Unix domain sockets only -C, - ...
- 高级功能:很有用的javascript自定义事件
之前写了篇文章<原生javascript实现类似jquery on方法的行为监听>比较浅显,能够简单的使用场景. 这里的自定义事件指的是区别javascript默认的与DOM交互的事件,比 ...
- THUSC2017 游记
你若安好,便是晴天. Day 0 中午就要出发了,上午浮躁的不行,根本写不下题去. 到了火车站之后发现教练和lyc和ztc在4车靠近5车的那一边,然而我在5车靠近4车的那边,尴尬…… 本来是想着上了火 ...
- egg.js-基于koa2的node.js入门
一.Egg.JS 简介 Egg.JS是阿里开发的一套node.JS的框架,主要以下几个特点: Egg 的插件机制有很高的可扩展性,一个插件只做一件事,Egg 通过框架聚合这些插件,并根据自己的业务场景 ...
- C#防止WebBrowser在新窗口中打开链接页面
在日常的开发中,大家有时需要用WebBrowser加载URL,来实现某些功能.而这时,我们就不希望所打开的页面中的链接,在新窗口中打开,因为这样的话,实际上是用系统默认的浏览器打开了,从而脱离了你的W ...
- 为什么选用 React 创建混合型移动应用?
[编者按]本文作者为 14islands 联合创始人.创新 Web 开发者 David Lindkvist,主要介绍有关混合型应用搭建的方方面面.文章系国内 ITOM 管理平台 OneAPM 编译呈现 ...
- zabbix系列之六——安装后配置二Items
https://www.zabbix.com/documentation/3.4/manual/config/items/itemtypes/snmp 1Items 1.1creating items ...
- leetCode题解之Reshape the Matrix
1.题目描述 2.分析 使用了一个队列. 3.代码 vector<vector<int>> matrixReshape(vector<vector<int>& ...
- SQL Server 索引知识-应用,维护
创建聚集索引 a索引键最好唯一(如果不唯一会隐形建立uniquier列(4字节)确保唯一,也就是这列都会复制到所有非聚集索引中) b聚集索引列所占空间应尽量小(否则也会使非聚集索引的空间变大) c聚集 ...
- Sql_从查询的结果集中分组后取最后有效的数据成新的结果集小记(待优化)
Dim sql As String = " SELECT xp.*, " sql = sql + " xf_owner.ownername, " sql = s ...