Javascript new关键字的玄机 以及其它


Posted in Javascript onAugust 25, 2010

(接上)先看张对老手不新鲜但对菜鸟很有趣的图:

Javascript new关键字的玄机 以及其它

What the heck is that? 简直是luan lun。

 

new

抛开上面的图,先看看上篇文章留下的第二个问题,让我们在构造器的函数体内加点东西,看会发生什么。

 

function A(){this.p = 1}
var a = new A()

会得到如下结果:

Javascript new关键字的玄机 以及其它

为什么用new关键字构造出来的a,会获得p这个属性?new A()这行代码做了什么事情?根据上篇文章中Function的创建过程第4步,A这个对象会有一个Construct属性(注意不是constructor,Consturct是ECMAScript标准里的属性,好像对外不可见),该属性的值是个函数,new A()即会调用A的这个Construct函数。那么这个Construct函数会做些啥呢?

1, 创建一个object,假设叫x。

2, 如果A.prototype是个object(一般都是),则把A.prototype赋给x.__proto__;否则(不常见),请大老板Object出马,把Object.prototype赋给x.__proto__。

3, 调用A.call(x),第一个参数传入我们刚刚创建的x。这就妥了,A的函数体里this.p = 1,这个this,就成了x。因此x就有了p这个属性,并且x.p = 1。

4, 一般情况下,就返回x了,这时a就是x了。但也有特殊情况,如果A的函数体里返回的东西,它的类型(typeof)是个object。那么a就不是指向x了,而是指向A函数返回的东西。

伪代码如下:

 

var x = new Object(); //事实上不一定用new来创建,我也不清楚。
x.__proto__ = A.prototype 
var result = A.call(x)
if (typeof(result) == "object"){
return result;
}
return x;

 

 

 

在我们的例子里,A函数返回undefined(因为没有return字眼),所以a就是x。但我们举个例子,验证下上面第4步里的特殊情况:

Javascript new关键字的玄机 以及其它

果然。

 

对象的constructor属性

再看看上篇文章留下的第一个问题

 

function Base(){}
Base.prototype.a = 1
var base = new Base();function Derived(){}
Derived.prototype = base;
var d = new Derived()

 

 

执行完上面的代码,mybase.constructor很容易猜到是Base,那么d.constructor呢?是Derived吗?

 Javascript new关键字的玄机 以及其它

不对,也是Base,怎么回事?很简单,复习下上篇的内容就知道:由于d本身没有constructor属性,所以会到d.__proto__上去找,d.__proto__就是Derived.prototype,也就是base这个对象,base也没constructor属性,于是再往上,到base.__proto__上找,也就是Base.prototype。它是有constructor属性的,就是Base本身。事实上,就我目前所知,只有构造器(function类型的object)的prototype,才真正自己拥有constructor属性的对象,且“构造器.prototype.constructor === 构造器”。

 

Instanceof

那么,instanceof怎么样?

Javascript new关键字的玄机 以及其它

从图中可以看出,d是Base、Derived和Object的实例。很合理,但这是怎么判断的呢?是这样的:对于x instanceof constructor的表达式,如果constructor.prototype在x的原型(__proto__)链里,那么就返回true。很显然,d的__proto__链往上依次是:Derived.prototype, Base.prototype, Object.prototype,得到图中结果就毫无疑问了。所以,instanceof跟对象的constructor属性无关。

 

Function and Object

最后解答一下文章开头的图。

Function和Object本身也是function类型的对象,因此可以说都是Function()构造出来的东西(自己构造自己,我不知道具体是不是这样,但就这么认为,挺合理的。)

也就是说,可以设想如下代码:

 

var Function = new Function()
var Object = new Function()

 

 

根据上篇文章的规律,会有Function.__proto__ === Function.prototype,以及Object.__proto__ === Function.prototype,验证一下:

Javascript new关键字的玄机 以及其它

Function instanceof Object,这是显然为true的,万物归Object管,Function的__proto__链依次指向:Function.prototype,Object.prototype。

Object instanceof Function,因为Function.prototype在Object的__proto__链中,所以也为true。

Javascript 相关文章推荐
可以文本显示的公告栏的js代码
Mar 11 Javascript
Jquery ThickBox插件使用心得(不建议使用)
Sep 08 Javascript
getElementByIdx_x js自定义getElementById函数
Jan 24 Javascript
js中hash和ico的关联分析
Feb 05 Javascript
JavaScript中数据结构与算法(一):栈
Jun 19 Javascript
jQuery实现仿QQ头像闪烁效果的文字闪动提示代码
Nov 03 Javascript
js实现密码强度检验
Jan 15 Javascript
BootStrap实现鼠标悬停下拉列表功能
Feb 17 Javascript
JavaScript设计模式--简单工厂模式定义与应用案例详解
May 23 Javascript
Vue 防止短时间内连续点击后多次触发请求的操作
Nov 11 Javascript
vue3+typeScript穿梭框的实现示例
Dec 29 Vue.js
Vue SPA 首屏优化方案
Feb 26 Vue.js
jquery下组织javascript代码(js函数化)
Aug 25 #Javascript
jquery实现居中弹出层代码
Aug 25 #Javascript
jquery下实现overlay遮罩层代码
Aug 25 #Javascript
在网页中使用document.write时遭遇的奇怪问题
Aug 24 #Javascript
javascript下string.format函数补充
Aug 24 #Javascript
javascript下利用arguments实现string.format函数
Aug 24 #Javascript
基于jQuery的淡入淡出可自动切换的幻灯插件
Aug 24 #Javascript
You might like
php 中include()与require()的对比
2006/10/09 PHP
实现dedecms全站URL静态化改造的代码
2007/03/29 PHP
解决dede生成静态页和动态页转换的一些问题,及火车采集入库生成动态的办法
2007/03/29 PHP
谈谈新手如何学习PHP 默默经典版本
2009/08/04 PHP
php数据库密码的找回的步骤
2011/01/12 PHP
ie与session丢失(新窗口cookie丢失)实测及解决方案
2013/07/15 PHP
php利用单例模式实现日志处理类库
2014/02/10 PHP
PHP GD库生成图像的几个函数总结
2014/11/19 PHP
PHP面试常用算法(推荐)
2016/07/22 PHP
浅谈Javascript中匀速运动的停止条件
2014/12/19 Javascript
jQuery实现滑动页面固定顶部显示(可根据显示位置消失与替换)
2015/10/28 Javascript
AngularJs  Using $location详解及示例代码
2016/09/02 Javascript
backbone简介_动力节点Java学院整理
2017/07/14 Javascript
微信小程序使用video组件播放视频功能示例【附源码下载】
2017/12/08 Javascript
JavaScript实现图片的放大缩小及拖拽功能示例
2019/05/14 Javascript
JQuery常见节点操作实例分析
2019/05/15 jQuery
layer的prompt弹出框,点击回车,触发确定事件的方法
2019/09/06 Javascript
[04:23]DOTA2上海特锦赛小组赛第一日 TOP10精彩集锦
2016/02/27 DOTA
python调用新浪微博API项目实践
2014/07/28 Python
Python多线程原理与用法实例剖析
2019/01/22 Python
python 二维数组90度旋转的方法
2019/01/28 Python
三星新西兰官网:Samsung新西兰
2019/03/05 全球购物
Groupon西班牙官方网站:在线优惠券和交易,节省高达70%
2021/03/13 全球购物
介绍一下Ruby的多线程处理
2013/02/01 面试题
各营销点岗位职责范本
2014/03/05 职场文书
聚美优品恶搞广告词
2014/03/14 职场文书
年终晚会主持词
2014/03/25 职场文书
新春文艺演出主持词
2014/03/27 职场文书
学校门卫岗位职责范本
2014/06/30 职场文书
英语自我介绍演讲稿
2014/09/01 职场文书
我的中国心演讲稿
2014/09/04 职场文书
杜甫草堂导游词
2015/02/03 职场文书
检讨书格式范文
2015/05/07 职场文书
2016党员学习心得体会范文
2016/01/23 职场文书
Nginx配置并兼容HTTP实现代码解析
2021/03/31 Servers
Django实现翻页的示例代码
2021/05/24 Python