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


Posted in Javascript onMay 07, 2013

如果用原型方式重定义前面例子中的类,它们将变为下列形式:

function ClassA() {
}
ClassA.prototype.color = "blue";
ClassA.prototype.sayColor = function () {
    alert(this.color);
};
function ClassB() {
}
ClassB.prototype = new ClassA();

原型方式的神奇之处在于最后一行代码。这里,把 ClassB 的 prototype 属性设置成 ClassA 的实例。这很有意思,因为想要 ClassA 的所有属性和方法,但又不想逐个将它们 添加到ClassB 的 prototype 属性。还有比把 ClassA 的实例赋予 prototype 属性更好的方法吗?

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

与对象冒充相似,子类的所有属性和方法都必须出现在 prototype 属性被赋值后,因为在它之前赋值的所有方法都会被删除。为什么?因为 prototype 属性被替换成了新对象,添加了新方法的原始对象将被销毁。所以,为 ClassB 类添加 name 属性和 sayName() 方法的代码如下:

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

可通过运行下面的例子测试这段代码:
var objA = new ClassA();
var objB = new ClassB();
objA.color = "blue";
objB.color = "red";
objB.name = "John";
objA.sayColor();
objB.sayColor();
objB.sayName();

此外,在原型链中,instanceof 运算符的运行方式也很独特。对 ClassB 的所有实例,instanceof 为 ClassA 和 ClassB 都返回 true。例如:
var objB = new ClassB();
alert(objB instanceof ClassA);    //输出 "true"
alert(objB instanceof ClassB);    //输出 "true"

在 ECMAScript 的弱类型世界中,这是极其有用的工具,不过使用对象冒充时不能使用该方法判断。但是由于子类的原型被直接重新赋值,所以出现以下这种情况:
console.log(objB.__proto__===objB.constructor.prototype)   //false

因为ClassB的原型链 prototype 属性被另一个类的对象重写了。输出结果可以看出objB.__proto__仍然指向的是ClassB.prototype,而不是objB.constructor.prototype。这也很好理解,给Person.prototype赋值的是一个对象直接量new ClassA()实例,使用对象直接量方式定义的对象其构造器(constructor)指向的是根构造器Object,Object.prototype是一个空对象{},{}自然与ClassB.prototype不等。
Javascript 相关文章推荐
js 函数调用模式小结
Dec 26 Javascript
js实现checkbox全选和反选示例
May 01 Javascript
探究Javascript模板引擎mustache.js使用方法
Jan 26 Javascript
JS当前页面登录注册框,固定DIV,底层阴影的实例代码
Sep 29 Javascript
js处理层级数据结构的方法小结
Jan 17 Javascript
Vuejs 用$emit与$on来进行兄弟组件之间的数据传输通信
Feb 23 Javascript
通过jquery的ajax请求本地的json文件方法
Aug 08 jQuery
解决vue v-for 遍历循环时key值报错的问题
Sep 06 Javascript
jquery操作select常见方法大全【7种情况】
May 28 jQuery
Bootstrap实现省市区三级联动(亲测可用)
Jul 26 Javascript
JS函数进阶之继承用法实例分析
Jan 15 Javascript
Vue基于iview实现登录密码的显示与隐藏功能
Mar 06 Javascript
基于JavaScript实现继承机制之构造函数+原型链混合方式的使用详解
May 07 #Javascript
使用javascript:将其它类型值转换成布尔类型值的解决方法详解
May 07 #Javascript
JQuery+CSS提示框实现思路及代码(纯手工打造)
May 07 #Javascript
基于IE下ul li 互相嵌套时的bug,排查,解决过程以及心得介绍
May 07 #Javascript
解决javascript:window.close()在chrome,Firefox下失效的问题
May 07 #Javascript
jQuery的slideToggle方法实例
May 07 #Javascript
jQuery实现动画效果的实例代码
May 07 #Javascript
You might like
php返回json数据函数实例
2014/10/09 PHP
Ubuntu中启用php的mail()函数并解决发送邮件速度慢问题
2015/03/27 PHP
smarty自定义函数用法示例
2016/05/20 PHP
PHP控制反转(IOC)和依赖注入(DI)
2017/03/13 PHP
laravel dingo API返回自定义错误信息的实例
2019/09/29 PHP
php libevent 功能与使用方法详解
2020/03/04 PHP
jquery多行滚动/向左或向上滚动/响应鼠标实现思路及代码
2013/01/23 Javascript
jQuery移除元素自动解绑事件实现思路及代码
2014/05/31 Javascript
NODE.JS加密模块CRYPTO常用方法介绍
2014/06/05 Javascript
jquery实现鼠标滑过后动态图片提示效果实例
2015/08/10 Javascript
node.js 动态执行脚本
2016/06/02 Javascript
AngularJS基础 ng-copy 指令实例代码
2016/08/01 Javascript
详解jQuery中基本的动画方法
2016/12/14 Javascript
微信小程序使用map组件实现获取定位城市天气或者指定城市天气数据功能
2019/01/22 Javascript
VUE脚手架的下载和配置步骤详解
2019/04/01 Javascript
如何检查一个对象是否为空
2019/04/11 Javascript
讲解python参数和作用域的使用
2013/11/01 Python
python正则表达式抓取成语网站
2013/11/20 Python
跟老齐学Python之模块的加载
2014/10/24 Python
在Python中使用mechanize模块模拟浏览器功能
2015/05/05 Python
Django中实现点击图片链接强制直接下载的方法
2015/05/14 Python
Python切片知识解析
2016/03/06 Python
深入学习Python中的装饰器使用
2016/06/20 Python
关于numpy.where()函数 返回值的解释
2019/12/06 Python
pytorch 利用lstm做mnist手写数字识别分类的实例
2020/01/10 Python
python基于pygame实现飞机大作战小游戏
2020/11/19 Python
HTML5对比HTML4的主要改变和改进总结
2016/05/27 HTML / CSS
英国最大的在线奢侈手表零售商:Jura Watches
2018/01/29 全球购物
英国现代家具和照明购物网站:Heal’s
2019/10/30 全球购物
波兰最大的电商平台:Allegro.pl
2021/02/06 全球购物
轻化专业学生实习自我鉴定
2013/09/20 职场文书
学习全国两会精神心得体会范文
2014/03/17 职场文书
毕业设计致谢语
2015/05/14 职场文书
离婚协议书范文2016
2016/03/18 职场文书
如何写好一份优秀的工作总结?
2019/06/21 职场文书
Python+OpenCV实现在图像上绘制矩形
2022/03/21 Python