返回

给this一个“家”——深入了解this的指向

前端

this的调用位置

this可以在函数、方法、构造函数和全局代码中被调用。

  • 在函数中,this指向函数所属的对象。例如,如果我们有一个函数名为myFunction,它属于对象myObject,那么当我们调用myFunction时,this将指向myObject

  • 在方法中,this指向该方法所属的对象。例如,如果我们有一个对象myObject,它有一个方法名为myMethod,那么当我们调用myObject.myMethod()时,this将指向myObject

  • 在构造函数中,this指向正在创建的新对象。例如,如果我们有一个构造函数名为MyConstructor,那么当我们调用new MyConstructor()时,this将指向新创建的对象。

  • 在全局代码中,this指向window对象。例如,如果我们在浏览器的控制台中输入this,那么它将输出window对象。

this的绑定规则

在JavaScript中,this的绑定规则非常复杂。它主要取决于函数的调用方式。

  • 默认绑定: 当一个函数被直接调用时,this指向全局对象(在严格模式下为undefined)。

  • 隐式绑定: 当一个函数被作为对象的方法调用时,this指向该对象。

  • 显式绑定: 我们可以使用call、apply或bind方法来显式地绑定this。

this的调用示例

下面是一些this的调用示例:

// 默认绑定
function myFunction() {
  console.log(this); // 输出window对象
}

myFunction(); // 调用myFunction

// 隐式绑定
const myObject = {
  myMethod() {
    console.log(this); // 输出myObject对象
  }
};

myObject.myMethod(); // 调用myObject.myMethod

// 显式绑定
function myFunction2(a, b) {
  console.log(this); // 输出window对象
}

myFunction2.call(myObject, 1, 2); // 调用myFunction2,并显式地绑定this到myObject

手写一个new的实现

我们还可以自己手写一个new函数来创建对象。下面是new函数的实现代码:

function new(constructor, ...args) {
  // 创建一个新对象
  const obj = {};

  // 将新对象的原型指向构造函数的原型
  obj.__proto__ = constructor.prototype;

  // 将this绑定到新对象
  const result = constructor.apply(obj, args);

  // 返回新对象
  return result instanceof Object ? result : obj;
}

练习题

  1. 在下面的代码中,this指向什么?
function myFunction() {
  console.log(this);
}

myFunction();
  1. 在下面的代码中,this指向什么?
const myObject = {
  myMethod() {
    console.log(this);
  }
};

myObject.myMethod();
  1. 在下面的代码中,this指向什么?
function myFunction2(a, b) {
  console.log(this);
}

myFunction2.call(myObject, 1, 2);
  1. 请使用new函数创建一个名为MyObject的对象,并输出对象的属性和方法。

  2. 请写一个函数,用于计算两个数的和,并使用call方法将this绑定到一个对象上,然后调用该函数。

总结

this是一个非常重要的概念,它在JavaScript中被广泛使用。理解this的指向对于编写出高质量的JavaScript代码至关重要。