javascript中的this指向总结(二)

1,021 阅读2分钟

「这是我参与2022首次更文挑战的第29天,活动详情查看:2022首次更文挑战」。

今天我们来学习总结下this的绑定规则。

  • 规则一:默认绑定
  • 规则二: 隐式绑定
  • 规则三: 显示绑定
  • 规则四: new绑定

本篇文章中将介绍规则一默认绑定和规则二隐式绑定。

规则一:默认绑定

什么情况下使用默认绑定呢?独立函数调用

独立函数调用我们可以理解为函数没有绑定到某个对象上进行调用,即函数没有调用主题。

接下来我们来看几个案例。

案例一

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

image.png 我们再来看下其他方式。

案例二

我们来思考下以下代码的三个this分别指向什么呢?

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

function foo2() {
  console.log(this);
  foo1()
}

function foo3() {
  console.log(this);
  foo2()
}

foo3()

foo1、foo2、foo3在调用的时候是独立调用,并没有通过info.foo1()等方式进行调用。 image.png 案例三

var obj = {
  name: 'haha',
  foo: function() {
    console.log(this);
  }
}

var bar = obj.foo
bar()

当我们调用foo函数的时候,也是独立调用,所以this指向的是window。

image.png 案例四

function foo() {
  console.log(this);
}
var obj = {
  name: 'haha',
  foo: foo
}
var bar = obj.foo
bar()

image.png 案例五

function foo() {
  function bar() {
    console.log(this);
  }
  return bar
}
var fn = foo()
fn()

image.png 接下来,我们改变一下案例五的调用方式,不直接调用fn。

var obj = {
  name: 'haha',
  eating: fn
}
obj.eating()

我们可以看到this指向的是obj对象,这是因为this进行了隐式绑定。我们接下来进行总结。 image.png

规则二: 隐式绑定

另外一种比较常见的调用方式是通过某个对象进行调用。也就是它的调用位置中,是通过某个对象发起的函数调用。

我们有个object对象,然后通过object.fn()进行调用。object对象会被js引擎绑定到fn函数中this里面。js引擎会自动帮助我们绑定,所以我们称之为隐式绑定。

案例一

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

var obj = {
  name: 'haha',
  foo: foo
}

obj.foo()

image.png 案例二

var obj = {
  name: 'haha',
  eating: function() {
    console.log(this.name + '在吃饭');
  },
  running: function() {
    console.log(this.name + '在跑步');
  }
}

obj.eating()
obj.running()

在这个例子中,由于obj调用了eating和running方法,所以this指向的obj对象,进行了隐式绑定。在上篇文章中,我们讲到了log中的this改成obj也是可以获取到obj对象中的name属性。

image.png 我们修改下调用方式,那么结果会是怎样呢?

var fn = obj.eating
fn()

以上是进行了独立绑定,this指向的window,而在window对象中本身是带有name属性的,但是name没有值。

image.png 打印window对象。

image.png 案例三

var obj1 = {
  name: 'obj1',
  foo: function() {
    console.log(this);
  }
}

var obj2 = {
  name: 'obj2',
  bar: obj1.foo
}

obj2.bar()

foo被调用的时候,它是被obj2进行调用起来的,obj2会自动绑定到foo中的this,所以foo中this指向的是obj2。

image.png