【5分钟一个知识点】JS一文搞懂new操作符
关于new操作符,看了两本书《Javascript高级程序设计3》和《你不知道的JS上》,以及其他文档后,终于豁然开朗。
现总结如下,希望同样懵逼的你,彻底理解它。
如果有不同的意见,欢迎留言讨论。
一、先看看两本书中的定义
《Javascript高级程序设计3》 第145页
1)创建一个新对象
2)将构造函数的作用域赋给新对象(因此this指向了这个新对象)
3)执行构造函数中的代码(为这个新对象添加属性)
4)返回新对象
《你不知道的JS上》第91页
1)创建(或者说构造)一个全新的对象
2)这个新对象会被执行[[Prototype]]连接
3)这个新对象会绑定到函数调用的this
4)如果函数没有返回其他对象,那么new表达式中的函数调用会自动返回这个新对象
二、那么,new到底做了什么?
简单来讲,它主要做了四步
1)创建一个新对象
2)将构造函数的prototype赋值给新对象的__proto__
3)构造函数中的this指向新对象,并且调用构造函数
4)如果构造函数无返回值,或者不是引用类型,返回新对象;否则为 构造函数的返回值。
PS:这里的引用类型,不清楚的,参见《高程3》的第5章;
三、自己手动实现new()
function New(){
var tmp_arr = Array.from(arguments);
var Func =tmp_arr[0];
//1、创建一个新对象:obj
var obj = {};
//2、将构造函数的prototype赋值给新对象的__proto__
obj.__proto__ = Func.prototype;
//3、将构造函数的this指向新对象obj,并且调用这个新对象
var result = Func.apply(obj,tmp_arr.slice(1,tmp_arr.length));
//如果返回值不是引用类型,返回obj。 否则返回 result
return result instanceof Object ? result : obj;
}
四、测试
第一种情况:无返回值
function New(){
var tmp_arr = Array.from(arguments);
var Func =tmp_arr[0];
var obj = {};
obj.__proto__ = Func.prototype;
var result = Func.apply(obj,tmp_arr.slice(1,tmp_arr.length));
return result instanceof Object ? result : obj;
}
function Func(name) {
this.name = name;
}
var f1 = new Func('f1');
console.log(f1);
var f2 = New(Func,'f2');
console.log(f2);
输出结果如下图
第二种情况:返回一个非引用类型
function New(){
var tmp_arr = Array.from(arguments);
var Func =tmp_arr[0];
var obj = {};
obj.__proto__ = Func.prototype;
var result = Func.apply(obj,tmp_arr.slice(1,tmp_arr.length));
return result instanceof Object ? result : obj;
}
function Func(name) {
this.name = name;
return true; //非引用类型
}
var f1 = new Func('f1');
console.log(f1);
var f2 = New(Func,'f2');
console.log(f2);
输出结果,同上!
第三种情况:返回一个引用类型,我们返回当前的日期 ;
function New(){
var tmp_arr = Array.from(arguments);
var Func =tmp_arr[0];
var obj = {};
obj.__proto__ = Func.prototype;
var result = Func.apply(obj,tmp_arr.slice(1,tmp_arr.length));
return result instanceof Object ? result : obj;
}
function Func(name) {
this.name = name;
return new Date(); //返回当前时间
}
var f1 = new Func('f1');
console.log(f1);
var f2 = New(Func,'f2');
console.log(f2);
输出结果,如下:

可以看出:我们的模拟的方法是正确的。
【5分钟一个知识点】JS一文搞懂new操作符的更多相关文章
- 一文搞懂如何使用Node.js进行TCP网络通信
摘要: 网络是通信互联的基础,Node.js提供了net.http.dgram等模块,分别用来实现TCP.HTTP.UDP的通信,本文主要对使用Node.js的TCP通信部份进行实践记录. 本文分享自 ...
- 一文搞懂 js 中的各种 for 循环的不同之处
一文搞懂 js 中的各种 for 循环的不同之处 See the Pen for...in vs for...of by xgqfrms (@xgqfrms) on CodePen. for &quo ...
- 基础篇|一文搞懂RNN(循环神经网络)
基础篇|一文搞懂RNN(循环神经网络) https://mp.weixin.qq.com/s/va1gmavl2ZESgnM7biORQg 神经网络基础 神经网络可以当做是能够拟合任意函数的黑盒子,只 ...
- Web端即时通讯基础知识补课:一文搞懂跨域的所有问题!
本文原作者: Wizey,作者博客:http://wenshixin.gitee.io,即时通讯网收录时有改动,感谢原作者的无私分享. 1.引言 典型的Web端即时通讯技术应用场景,主要有以下两种形式 ...
- 三文搞懂学会Docker容器技术(中)
接着上面一篇:三文搞懂学会Docker容器技术(上) 6,Docker容器 6.1 创建并启动容器 docker run [OPTIONS] IMAGE [COMMAND] [ARG...] --na ...
- 一文搞懂所有Java集合面试题
Java集合 刚刚经历过秋招,看了大量的面经,顺便将常见的Java集合常考知识点总结了一下,并根据被问到的频率大致做了一个标注.一颗星表示知识点需要了解,被问到的频率不高,面试时起码能说个差不多.两颗 ...
- 一文搞懂Flink Window机制
Windows是处理无线数据流的核心,它将流分割成有限大小的桶(buckets),并在其上执行各种计算. 窗口化的Flink程序的结构通常如下,有分组流(keyed streams)和无分组流(non ...
- 一文搞懂RAM、ROM、SDRAM、DRAM、DDR、flash等存储介质
一文搞懂RAM.ROM.SDRAM.DRAM.DDR.flash等存储介质 存储介质基本分类:ROM和RAM RAM:随机访问存储器(Random Access Memory),易失性.是与CPU直接 ...
- 一文搞懂 Prometheus 的直方图
原文链接:一文搞懂 Prometheus 的直方图 Prometheus 中提供了四种指标类型(参考:Prometheus 的指标类型),其中直方图(Histogram)和摘要(Summary)是最复 ...
随机推荐
- 一起使用mock数据动态创建表格
在ant-design中,我们创建一个基础table会怎么实现呢? 如下代码可视,我们会自己创建一些数据,在表格中渲染出来,如下 <Card title="基础表格"> ...
- EClipse for PHP 中文乱码问题
UTF-8 格式的php,中文都是乱码. 如果此时在EClipse中输入中文会有 CP1252 错误( CP1252不支持xxxx ) 解决方法: windows->preferences-&g ...
- springcloud的配置文件的读取顺序
SpringBoot默认支持properties和YAML两种格式的配置文件.前者格式简单,但是只支持键值对.如果需要表达列表,最好使用YAML格式.SpringBoot支持自动加载约定名称的配置文件 ...
- CodeForces701E DFS
http://codeforces.com/problemset/problem/701/E 一个显而易见的方法是考虑点的贡献,一次dfs记录到所有根节点不考虑匹配的答案,再一次dfs反向推出答案 # ...
- pyautogui_pdf批量转换为TXT
pyautogui_pdf批量转换为TXT, 用pdf自带无损转换 # -*- coding: utf-8 -*- """ Created on Thu May 5 15 ...
- selenium_采集药品数据
Python爬虫视频教程零基础小白到scrapy爬虫高手-轻松入门 https://item.taobao.com/item.htm?spm=a1z38n.10677092.0.0.482434a6E ...
- xgboost应用
在业务中,我们经常需要对数据建模并预测.简单的情况下,我们采用 if else 判断(一棵树)即可.但如果预测结果与众多因素有关,而每一个特征的权重又不尽相同. 所以我们如何把这些特征的权重合理的找出 ...
- JVM总结(六):早期(编译期)优化
这节我们来总结一下JVM编译器优化问题. JVM编译器优化 Javac编译器 Javac的源码和调试 解析与填充符号表 注解处理器 语法分析与字节码生成 Java语法糖 泛型和类型擦除 自动装箱.拆箱 ...
- js通用绑定事件函数
- 单例设计模式Singleton之懒加载模式(懒汉模式)【原】
单例设计模式Singleton之懒加载模式(懒汉模式) SingletonLazy.java类 package kingtool; import kingtool.http.IPTool; publi ...