new函数作用
要想知道new函数怎么实现,首先要清楚new函数的功能。
- 首先是新建一个函数
- 这个新函数的
prototype指向构造函数的prototype属性 - 构造函数内部的
this指向新函数 - 为新对象添加属性
- 返回这个新对象
es6为
new函数添加了target属性,允许你检测函数或构造方法是否是通过new方式被调用的。new.target返回一个指向构造方法或函数的引用.
实现代码
// 实现方法
function myNew () {
// 获取传入的函数
let constructor = arguments[0];
if (typeof constructor !== 'function') {
throw ('第一个参数必须为function类型!');
}
// new.target指向这个函数
myNew.target = constructor;
// 获取函数外的其他参数
let args = [].slice.call(arguments, 1);
// let obj = {};
// obj.__proto__ = constructor.prototype;
// 1.新建一个函数
// 2.这个新对象内部的 [[Prototype]] 指针被赋值为构造函数(constructor)的 prototype 属性
let obj = Object.create(constructor.prototype);
// 3. 构造函数内部的 this 被赋值为这个新对象(即 this 指向新对象)
// 4. 执行构造函数内部的代码(给新对象添加属性)
let res = constructor.apply(obj, args);
// 5. 如果构造函数返回非空对象,则返回该对象;否则,返回刚才创建的新对象
if (res !== null && (typeof res === 'object' || typeof res === 'function')) {
return res;
}
return obj;
}
// 测试方法
function person (name, age) {
// console.log('this:', this);
// console.log('new.target:', new.target);
// console.log('useNewOperator.target:', myNew.target);
this.name = name;
this.age = age;
}
person.prototype.sayName = function () {
console.log(this.name);
};
const p1 = new person('new', 20);
console.log(p1, p1.target);
p1.sayName();
const p2 = myNew(person, 'zhang', 18);
console.log(p2, p2.target);
p2.sayName();