定义:
this 是 JavaScript 中的一个关键字,是函数运行时,自动生成的一个内部对象,只能在函数内部使用,this 总是指向调用函数的那个对象。
默认绑定
默认绑定我们可以这样理解,在调用函数的时候,函数前无任何调用前缀的情景。比如:定义一个函数(比如函数foo),通过 foo() 来调用。
在默认绑定的情况下,有严格模式和非严格模式两种。在非严格模式下,this 指向全局对象(在浏览器中指向 window)。在严格模式下,this 的值为 undefined。
// 非严格模式下
function foo() {
console.log('this-----------------------------', this) // window
}
foo()
// 严格模式下
'use strict'
function foo() {
console.log('this-----------------------------', this) // undefined
}
foo()
如上述代码所示,默认绑定的情况下,非严格模式,this 指向全局对象,严格模式,this 为 undefined。
ps: 自调用的函数 this 指向哪里?
// 非严格模式下
(function foo() {
console.log('this-----------------------------', this) // window
})()
// 严格模式下
'use strict';
(function foo() {
console.log('this-----------------------------', this) // undefined
})()
如上述代码所示,默认绑定的情况下,自调用函数在非严格模式,this 指向全局对象,严格模式,this 为 undefined。由此可见,自调用函数与普通函数的默认绑定方式中的 this 指向相同。
隐式绑定
函数可以被对象作为方法进行调用,这时函数中的 this 指向上一级对象。
var obj = {
a: 1,
fn: function () {
console.log('this-----------------------------', this, this === obj) // obj true
}
}
obj.fn()
通过结果我们可知,通过对象的方法调用的函数中的 this 指向该方法所在的上一层的对象,如果对象中嵌套对象,this 指向哪里,实现代码并运行结果如下:
var obj = {
a: 1,
b: {
a: 2,
fn: function () {
console.log('this-----------------------------', this, this === obj.b) // obj true
}
}
}
obj.b.fn()
由以上可知,this 指向该方法所在的上一层的对象,即 obj.b 对象,符合隐式绑定的原则。
有一个特殊的情况:就是当把对象中的方法赋值给一个变量的时候,这是相当于定义了普通的函数。
var obj = {
a: 1,
fn: function () {
console.log('this-----------------------------', this, this === obj) // window false
}
}
let foo = obj.fn
foo()
将 obj.fn 赋值给了变量 foo,再进行调用,则是相当于普通函数的调用,因此该this 指向了 window。
显示改变 this 指向
我们可以通过 call, apply 和 bind 来显示改变 this 的指向,指向 call, apply, bind 的第一个参数 。以 call为例:
function foo() {
console.log('this-----------------------------', this) // obj
}
var obj = {
a: 1
}
foo.call(obj) // obj
运行结果如下,通过 call 将函数的 this 指向了 obj。通过 apply, bind 可以得到同样的结果。
// bind 函数
function foo() {
console.log('this-----------------------------', this) // obj
}
var obj = {
a: 1
}
var fn = foo.bind(obj)
fn() // obj
// apply 函数
function foo() {
console.log('this-----------------------------', this) // obj
}
var obj = {
a: 1
}
foo.apply(obj)
new 绑定
通过 new 生成一个实例对象, this 指向这个实例对象。
function Person(name) {
this.name = name
}
let person = new Person('maomao')
console.log('person-----------------------------', person.name) // maomao
如果构造函数 Person 显示的返回一个对象的时候。this 指向该返回的对象。
function Person(name) {
this.name = name
return {
name: 'amao'
}
}
let person = new Person('maomao')
console.log('person-----------------------------', person.name) // amao
以上就是有关 this 的指向问题,希望对大家有所帮助。