JS中new到底发生了什么
outline
prototype与__proto__function与objectnew到底发生了什么
prototype 与 __proto__
首先说下在JS中比较容易让人困惑的 prototype 和 __proto__ __proto__ 就是JavaScript中所谓的原型.
一个对象的 __proto__ 属性和自己的内部属性[[Prototype]]指向一个相同的值 (通常称这个值为原型),原型的值可以是一个对象值也可以是null(比如说Object.prototype.__proto__ 的值就是null).该属性可能会引发一些错误,因为用户可能会不知道该属性的特殊性,而给它赋值,从而改变了这个对象的原型. 如果需要访问一个对象的原型,应该使用方法Object.getPrototypeOf.
firefox、chrome等浏览器把对象内部属性[[Prototype]]用 __proto__ 的形式暴露了出来.(老版本的IE并不支持 __proto__ ,IE11中已经加上了 __proto__ 属性)
prototype 是function中特有的.什么意思呢?举个例子:
function A(name){
this.name = name;
}
console.dir(A);
我们得到如下结果:

首先看A是一个函数,自然A的原型链就应该指向一个函数对象.
其次我们还看到当我们定义了function A的时候,A上会有一个 prototype 的属性.这个属性是我们定义function的时候就默认带上的.A的 prototype 指向一个对象,这个对象的包含一个 constructor 属性以及一个 __proto__ ( __proto__ 指向Object表示这是一个对象).默认的constructor属性指向function A.
看起来有点混乱是不?这边只要记住一点: __proto__ 是原型,prototype是函数默认的一个属性,它指向一个对象,这个对象的constructor属性指向函数本身.
function与object
首先看一个例子
function A(name){
this.name = name;
this.getName = function(){
console.log(this.name);
}
var b = 'test';
console.log(b);
}
var a = new A('testa');
A('TESTA');
当执行 var a = new A('testa'); 得到的a是这样的:

而我们执行 A('TESTA'); 相当于:
//window.name = 'TESTA'(由于非strict模式下,this默认指向window)
//window.getName = function(){console.log(this.name);}
我们的函数A既可以直接执行,又可以new一下返回一个对象.function和object到底是什么关系,new的时候发生了什么?
new到底发生了什么
还是我们上面的问题,当我们执行 var a = new A('testa') 到底发生了什么.MDN上是这么说的
对于 var o = new Foo();
//JavaScript 实际上执行的是:
var o = new Object();
o.[[Prototype]] = Foo.prototype;
Foo.call(o);
这样大概就明白了,当我们执行 new A('testa') 的时候
JS会这样做
- var o = new Object();
- o.
__proto__= A.prototype;//这里还记得之那个function里面的默认的属性么? - A.call(o)//由于这里this是指向o,可以把什么this.name/getName绑定到o上.
- 把这个o返回给a;//完成var a = new A()的过程.
这里注意下,上面所谓的第4步其实是一个简化的说法.真正的过程是在第3步之后,如果发现A返回是一个Object类型(非primitive类型,即非string,boolean,number,null,undefined类型就是Object类型),则直接返回A的返回值,否则把第1步new的Object返回出去.(默认情况下,JS中函数默认返回值是undefined)举个例子
function A(name){
this.name = name;
this.getName = function(){
console.log(this.name);
}
var b = 'test';
console.log(b);
return {};
}
var a = new A('testa');//{}
这里我们把A函数的返回值设置为一个Object类型,则这个时候执行new A返回的就是A函数的返回值{}.如果我们把A的返回值设置为return [];那么我们在new A的时候也相应的得到一个空数组.
用 stackoverflow 上一个人的回答来总结下就是:
In JavaScript, most functions are both callable and instantiable: they have both a [[Call]] and [[Construct]] internal methods.
在JS中,绝大多数的函数都是既可以调用也可以实例化的.我们既可以直接执行函数得到函数的返回值.也可以通过new操作符得到一个对象.
原文地址:http://warjiang.github.io/devcat/2016/05/12/JS中new到底发生了什么/
JS中new到底发生了什么的更多相关文章
- js 中this到底指向哪里?
其实js的this指向很简单.我们记住下面3种情况. this 指向的是浏览器中的window.代码如下: function fn(){ this.name='yangkun'; this.age=2 ...
- js中‘0’到底是 true 还是 false
if ('0') alert("'0' is true"); if ('0' == false) alert("'0' is false");结果是,两次都 ...
- JS 中new一个对象发生了什么事
今天看到一个360的前端面试题: function A(){}function B(a){ this.a=a;}function C(a){ if(a){ this.a=a; }}A.p ...
- JS中this到底指哪个对象
忘了原作者是谁了 自己也添加了一些东西 勉强可以观看一下 元素就不写了 可以自己添一下试试 先看这段代码 target.onclick = function(){ console.log(t ...
- js中new到底做了什么?如何重写new?
new 构造函数()执行顺序1.在堆中开辟对象内存空间, 记为obj2.在obj 中添加__proto__属性并指向 构造函数.prototype3.将构造函数中的this 指向obj4.执行构造函数 ...
- JS中this到底指向谁?
关于this的指向,是一个令人很头疼的问题.但是,你运气好,碰到了我.老夫这儿有本祖传秘籍,看懂这个,妈妈再也不用担心你的this指向不对啦! 归根结底,this指向就一句话:谁最终调用函数,this ...
- js中new到底做了什么?
1.创建一个新的obj; 2.让obj_proto_=Func.prototype; 3.Func.call(obj);
- Js new到底发生了什么
在Js中,我们使用了new关键字来进行实例化 那么在这个new的过程中到底发生了什么? 关于构造函数的return 正常来讲构造函数中是不用写return语句的,因为它会默认返回新创建的对象. 但是, ...
- js中this和回调方法循环-我们到底能走多远系列(35)
我们到底能走多远系列(35) 扯淡: 13年最后一个月了,你们在13年初的计划实现了吗?还来得及吗? 请加油~ 主题: 最近一直在写js,遇到了几个问题,可能初入门的时候都会遇到吧,总结下. 例子: ...
随机推荐
- HDU2459 后缀数组+RMQ
题目大意: 在原串中找到一个拥有连续相同子串最多的那个子串 比如dababababc中的abababab有4个连续的ab,是最多的 如果有同样多的输出字典序最小的那个 这里用后缀数组解决问题: 枚举连 ...
- 转-httpd 2.4.4 + mysql-5.5.28 + php-5.4.13编译安装过程
一.编译安装apache 1.解决依赖关系 httpd-2.4.4需要较新版本的apr和apr-util,因此需要事先对其进行升级.升级方式有两种,一种是通过源代码编译安装,一种是直接升级rpm包.这 ...
- 用JS获取地址栏参数的方法(超级简单)
方法一:采用正则表达式获取地址栏参数:( 强烈推荐,既实用又方便!) function GetQueryString(name) { var reg = new RegExp("( ...
- java中“/0”含义
public class Test { public static void main(String[] args) { // 正常情况下,对这个0,tp中储的是其对应的ASCII码48 char t ...
- 转载《遭受arp攻击怎么办》
ARP(Address Resolution Protocol,地址解析协议)协议的基本功能就是通过目标设备的IP地址,查询目标设备的MAC地址,以保证通信的进行.ARP攻击仅能在以太网(局 域网如: ...
- java常用基础知识点 (持续追加)
作为一个Java编程人,会经常用上JDK中的大量的API类库,常用的有字符串操作.集合操作.文本操作.输入输出操作.以及网络操作, 常用的包: 1. java.lang Java程序的基础类,字符串, ...
- CSS 透明度 设置 兼容IE FF
filter:Alpha(Opacity=80);/*IE*/ -moz-opacity:0.8;/*FF*/ opacity: 0.8;/*所有元素*/ 参数设置说明: Alpha(Opacity= ...
- 【转】 linux 下Time_wait过多问题解决
问题起因: 自己开发了一个服务器和客户端,通过短连接的方式来进行通讯,由于过于频繁的创建连接,导致系统连接数量被占用,不能及时释放.看了一下18888,当时吓到了. 现象: 1.外部机器不能正常连接S ...
- eap-peap/mschapv2
eap-peap/mschapv2 文件路径 用途 示例 备注 #gedit /usr/local/etc/raddb/sites-available/default #gedit /us ...
- Data Binding和INotifyPropertyChanged是如何协调工作的?
前言 WPF的一大基础就是Data Binding.在基于MVVM架构的基础上,只有通过实现INotifyPropertyChanged接口的ViewModel才能够用于Data Binding. 要 ...