结论:
- 普通函数和匿名函数中的this指向是在运行时候确定的,谁调用了该函数,那么this就指向谁;找不到调用者的时候,那么调用者就是window,此时this指向window对象。
- 箭头函数中的this指向的是父级作用域中的this的指向,或者说,该箭头函数在哪定义的,那么箭头函数中this就指向哪块作用域。
- 在严格模式下,即’use strict’模式下,全局作用域下的普通函数和匿名函数中的this指向undefine。
- 构造函数中的this指向实例化后的对象,因为在使用new关键字进行实例化的时候,改变了this的指向。
以下例子显示了在各种情况下this的指向:
var a = 0;
console.log(this.a); //this指向window
var a = 0;
function f1() {
console.log(this.a); //this指向window
}
f1();
var a = 0;
let obj = {
a: 1,
showA: function () {
console.log(this.a); //打印1,this指向obj
},
};
obj.showA();
var a = 0;
let obj = {
a: 1,
showA: () => {
console.log(this.a); //打印0,this指向window
},
};
obj.showA();
/**
* @name:普通函数
* @msg:
* @param {*}
* @return {*}
*/
function foo() {
console.log(this.a); //非严格模式下this指向widnow,严格模式下this指向undefine
}
var a = 2;
foo();
/**
* @name:匿名函数
* @msg:
* @param {*}
* @return {*}
*/
var foo = function () {
console.log(this.a); //非严格模式下this指向widnow,严格模式下this指向undefine
};
var a = 2;
foo();
//构造函数版this
function Fn(){
this.user = "追梦子";
}
var a = new Fn();
console.log(a.user); //追梦子,this指向a对象
在Vue组件中:
//使用匿名函数
methods: {
inited(viewer) {
setTimeout(function () {
console.log(this);//打印window对象,这里的this指向window。因为这里找不到具体是谁调用了这个匿名函数,所以这里this指向window
}, 10000);
},
}
//针对上面的例子,如何改变this的指向
methods: {
inited(viewer) {
setTimeout(function () {
console.log(this);//使用bind()函数改变this指向后,this则指向vue实例
}.bind(this), 10000);
},
}
//使用箭头函数
methods: {
inited(viewer) {
setTimeout(()=> {
console.log(this);//打印vue对象,这里的this指向vue实例,因为这里的箭头函数中的this指向父作用域中的this的指向。
}, 10000);
},
}
在Vue组件中使用箭头函数的一种特殊情况:
这里的指向和vue源码有关,具体原因分析参考:为什么在vue中的methods中箭头函数的this指向undefined
methods: {
inited:(viewer)=> {
console.log(this);//此时this指向undefine。
},
}