new 操作符

7/30/2021 Javascript

# new 操作符做了什么

  • 创建的一个空的 js 对象,即就是{}
  • 将空对象的原型 prototype 指向构造函数的原型
  • 将空对象作为构造函数的上下文,即改变 this 的指向
  • 对构造函数有返回值的判断
  1. 如果返回值是基础数据类型,则忽略返回值,返回 new 操作符生成的对象
  2. 如果返回值是引用数据类型,则使用 return 的返回,也就是操作符无效
function Person(name) {
    this.name = name;
    return 1;
}
let me = new Person('april');
console.log(me); // {name: 'april'}
1
2
3
4
5
6
function Person(name) {
    this.name = name;
    console.log('hahah', [].shift.call(arguments));
    return { age: 12 };
}
let me = new Person('april');
console.log(me); // {age: 12}
1
2
3
4
5
6
7

# 模拟实现

new 是关键字,无法直接覆盖,定义一个函数来模拟 new 的效果

function objectFactory() {
    let obj = new Object();
    Constructor = [].shift.call(arguments);
    obj.__proto__ = Constructor.prototype;
    let result = Constructor.apply(obj, arguments);
    // typeof null 返回的也是object
    return typeof result === 'object' ? result || obj : obj;
}
1
2
3
4
5
6
7
8

# 模拟方法使用

function Person(name) {
    this.name = name;
}
let result = objectFactory(Person, 'april');
console.log(result); // { name: 'april'}
1
2
3
4
5

# 注意

三种创建空对象的区别 三种创建空对象的区别

所以由 Object.create 生成的对象,调用原型上的方法会报错

function objectFactory() {
    let obj = Object.create(null);
    Constructor = [].shift.call(arguments);
    obj.__proto__ = Constructor.prototype;
    let result = Constructor.apply(obj, arguments);
    // typeof null 返回的也是object
    return typeof result === 'object' ? result || obj : obj;
}
function Person(name) {
    this.name = name;
}
Person.prototype.say = function() {
    console.log('hello');
};
let result = objectFactory(Person, 'april');
result.say(); // Uncaught TypeError: result.say is not a function
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
上次更新: 4/29/2022, 12:51:22 PM