返回

深入剖析JavaScript中this的指向:标准函数与箭头函数的差异

前端

JavaScript中的this:标准函数与箭头函数的差异

标准函数中的this

在标准函数中,this指向调用它的对象。如果函数不是作为对象的方法被调用,那么this指向全局对象window。例如:

function sayHello() {
  console.log(this);
}

sayHello(); // 输出:window

如果函数作为对象的方法被调用,那么this指向调用它的对象。例如:

const person = {
  name: "John",
  sayHello: function() {
    console.log(this);
  }
};

person.sayHello(); // 输出:{ name: "John", sayHello: [Function: sayHello] }

箭头函数中的this

在箭头函数中,this指向创建它的函数所在的作用域。如果箭头函数是在全局作用域创建的,那么this指向全局对象window。例如:

const sayHello = () => {
  console.log(this);
};

sayHello(); // 输出:window

如果箭头函数是在对象的方法中创建的,那么this指向创建它的对象。例如:

const person = {
  name: "John",
  sayHello: () => {
    console.log(this);
  }
};

person.sayHello(); // 输出:window

值得注意的是,箭头函数没有自己的this绑定。这意味着你不能使用call()、apply()或bind()方法来改变箭头函数的this指向。

总结

总之,标准函数中的this指向调用它的对象,而箭头函数中的this指向创建它的函数所在的作用域。这可能会导致一些令人困惑的情况,因此在使用this时一定要小心。

示例

为了更好地理解this在标准函数和箭头函数中的区别,让我们来看一些示例:

示例一

function Person(name) {
  this.name = name;

  this.sayHello = function() {
    console.log(`Hello, my name is ${this.name}.`);
  };
}

const person = new Person("John");
person.sayHello(); // 输出:Hello, my name is John.

在这个示例中,标准函数sayHello()作为Person对象的方法被调用,因此this指向调用它的对象person。

示例二

const sayHello = () => {
  console.log(`Hello, my name is ${this.name}.`);
};

const person = {
  name: "John",
  sayHello: sayHello
};

person.sayHello(); // 输出:Uncaught TypeError: Cannot read properties of undefined (reading 'name')

在这个示例中,箭头函数sayHello()作为Person对象的方法被调用,但由于箭头函数没有自己的this绑定,所以this指向全局对象window。由于window对象没有name属性,因此会报错。

示例三

const Person = {
  name: "John",
  sayHello: function() {
    setTimeout(() => {
      console.log(`Hello, my name is ${this.name}.`);
    }, 1000);
  }
};

Person.sayHello(); // 输出:Hello, my name is undefined.

在这个示例中,setTimeout()函数中的箭头函数没有自己的this绑定,因此this指向全局对象window。由于window对象没有name属性,因此会输出undefined。

结论

JavaScript中的this是一个复杂的话题,但只要理解了标准函数和箭头函数中this的不同行为,就能避免许多常见的错误。