JavaScript this

90 阅读2分钟

this

this关键字是JavaScript中最复杂的机制之一,它被自动定义在所有函数的作用域中。

———— 《你不知道的JavaScript 上》

一、this 是什么

  1. 随着代码的复杂程度提升,显式的传递上下文对象,会让代码越来越混乱,所以this 提供了一种更优雅的方式隐式的“传递”一个对象引用,因此api可以更加简洁并且易于复用

  2. this的上下文取决于函数调用时的各种条件,this的绑定和函数声明的位置没有任何关系只取决于函数的调用方式

二、判断this的方式

调用位置

找到函数被调用的位置,判断this的引用是什么

绑定规则

1. 默认绑定
let a = 2 ;
function foo(){
    console.log(this.a);
}
foo() // 2  this指向了全局对象a

2. 隐式绑定

对象属性的引用只有最后一层调用生效。

const user = {
    name:'小明'
    seename:seename //注意此处声明,函数上下文发生了变化
}
function seename(){
    consoel.log(this.name) 
}
user.seename()// 小明

3. 显式绑定 (直接指定this的值)

在函数传参时使用 call()apply() 方法 .

call()的第一个参数会被传递给this apply() 方法接受数组形式的参数,第一个参数会被传递给this。

let name='小明'
function seename(){
    console.log(this.name)
}
seename.call('小张')// 小张

4. 硬绑定 function.prototype.bind()

bind()  方法创建一个新的函数,在 bind() 被调用时,这个新函数的 this 被指定为 bind() 的第一个参数,而其余参数将作为新函数的参数,供调用时使用。

const module = {
  x: 42,
  getX: function() {
    return this.x;
  }
};

const unboundGetX = module.getX;
console.log(unboundGetX()); // undefined 注意此时unboundGetX函数的调用位置是全局上下文

const boundGetX = unboundGetX.bind(module);
console.log(boundGetX()); //  42

5. new绑定

new在构造函数的时候做了什么?

  1. 创建(构造)一个新的对象
  2. 将对象绑定到构造函数的原型 (prototype)
  3. 这个对象会绑定到函数调用的this
  4. 如果没有返回其他对象,那么new 表达式中的函数调用会自动返回这个新对象