Skip to content
On this page

为什么需要 this?

在常见的编程语言中,几乎都有 this 这个关键字(Objective-C 中使用的是 self),但是 JavaScript 中的 this 和常见的面向对象语言中的 this 不太一样:

  • 常见面向对象的编程语言中,比如 Java、C++、Swift、Dart 等等一系列语言中,this 通常只会出现在类的方法中。
  • 也就是你需要有一个类,类中的方法(特别是实例方法)中,this 代表的是当前调用对象。
  • 但是 JavaScript 中的 this 更加灵活,无论是它出现的位置还是它代表的含义。

我们来看一下编写一个 obj 的对象,有 this 和没有 this 的区别

javascript
var obj = {
  name: "wjw",
  running: function () {
    console.log(obj.name + "running");
  },
  eating: function () {
    console.log(obj.name + "eating");
  },
  studying: function () {
    console.log(obj.name + "studying");
  },
};
1
2
3
4
5
6
7
8
9
10
11
12
javascript
var obj = {
  name: "wjw",
  running: function () {
    console.log(obj.name + "running");
  },
  eating: function () {
    console.log(obj.name + "eating");
  },
  studying: function () {
    console.log(obj.name + "studying");
  },
};

// 使用 this 后
var obj = {
  name: "wjw",
  running: function () {
    console.log(this.name + "running");
  },
  eating: function () {
    console.log(this.name + "eating");
  },
  studying: function () {
    console.log(this.name + "studying");
  },
};
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26

定义

函数的 this 关键字在 JavaScript 中的表现略有不同,此外,在严格模式和非严格模式之间也会有一些差别

在绝大多数情况下,函数的调用方式决定了 this 的值(运行时绑定)

this 关键字是函数运行时自动生成的一个内部对象,只能在函数内部使用,总指向调用它的对象

javascript
function baz() {
  // 当前调用栈是:baz
  // 因此,当前调用位置是全局作用域

  console.log("baz");
  bar(); // <-- bar的调用位置
}

function bar() {
  // 当前调用栈是:baz --> bar
  // 因此,当前调用位置在baz中

  console.log("bar");
  foo(); // <-- foo的调用位置
}

function foo() {
  // 当前调用栈是:baz --> bar --> foo
  // 因此,当前调用位置在bar中

  console.log("foo");
}

baz(); // <-- baz的调用位置
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24

同时,this 在函数执行过程中,this 一旦被确定了,就不可以再更改

javascript
var a = 10;
var obj = {
  a: 20
}

function fn() {
  this = obj; // 修改this,运行后会报错
  console.log(this.a);
}

fn();
1
2
3
4
5
6
7
8
9
10
11
沪ICP备20006251号-1