一、关于new运算符
这篇博客主要关注如何实现new运算符,不太了解new的同学可以看看这篇博客
链接: 谈谈JS new运算符到底做了些什么
二、前期准备: 实现一个new运算符需要做哪些事情
- 创建一个空对象 instance
- 绑定构造函数的this,使其指向instance,执行构造函数为instance设置属性
- 将instance的原型链指向构造函数的原型
- 如果构造函数指定了引用类型的返回值ret,那么返回ret,否则返回instance
既然准备好了,接下来就开始撸代码吧~
三、实现JavaScript new运算符
代码如下
function _new(ctor) {
if (typeof ctor !== 'function') {
throw 'first parameter must be a function !'
}
// 创建实例,链接原型
var instance = Object.create(ctor.prototype)
// 提取形参列表
var params = Array.prototype.slice.call(arguments, 1)
// 绑定this,设置属性,获取构造函数的返回值
var customReturn = ctor.call(instance, ...params)
// 如果构造函数自身有引用类型的返回值,那么返回自身,否则返回instance
var isCustomReturnAvailable = typeof customReturn === 'object' || typeof customReturn === 'function'
// ES6 new.target一般在函数体中使用,在构造函数中返回函数的引用,在普通函数中返回undefined
_new.target = ctor
return isCustomReturnAvailable ? customReturn : instance
}
测试用例
function Apple(size) {
this.size = size
}
function CustomApple() {
return {
size: 'big'
}
}
Apple.prototype.color = 'red'
console.log(_new(Apple, 'huge')) // Apple { size: 'huge' }
console.log(new Apple('huge')) // Apple { size: 'huge' }
console.log(_new(CustomApple, 'huge')) // { size: 'big' }
结果