什么是this?
在JS中,this其實是多余的,它的作用是讓JS看起來像JAVA,this我理解為當前的執行環境。
全局中的this
全局中的this一般指向全局對象,瀏覽器中的全局對象就是 window。如:
console.log(this.document === document); //true
console.log(this === window); //true
this.a = 1234;
console.log(window.a); //1234
普通函數的 this
一般函數的 this也是指向 window,在 nodeJS 中為 global object。如:
function fn () {
return this;
}
console.log(fn() === window);//true, global object
需要注意的是在嚴格模式中,函數的 this 為 undefined,因為嚴格模式禁止this關鍵字指向全局對象:
function a1 () {
"use strict";//使用嚴格模式
return this;
}
console.log(a1() === undefined);//true
對象方法的函數的 this
var o = {
age: 18,
f: function() {
return this.age;
}
};
console.log(o.f()); // 18
f 為對象 o 的方法。這個方法的 this 指向這個對象,在這里即對象 o。
普通函數調用
函數也可以直接被調用,此時 this 綁定到全局對象。在瀏覽器中,window 就是該全局對象。
window.name = 'globalName';
var getName = function(){
return this.name
};
console.log(getName());//globalName
對象原型鏈上的this
var o = {
f: function() {
return this.a + this.b;
}
};
var p = Object.create(o);
p.a = 1;
p.b = 2;
console.log(p.f()); //3
通過 var p = Object.create(o) 創建的對象,p 是基于原型 o 創建出的對象。
p 的原型是 o,調用 f() 的時候是調用了 o 上的方法 f(),這里面的 this 是可以指向當前對象的,即對象 p。
構造器中的 this
function MyClass() {
this.a = 25;
}
var o = new MyClass();
console.log(o.a); //25
new MyClass() 的時候,MyClass()中的 this 會指向一個空對象,這個對象的原型會指向 MyClass.prototype。MyClass()沒有返回值或者返回為基本類型時,默認將 this 返回。
function a2() {
this.a = 18;
return {
a: 28
};
}
o = new a2();
console.log(o.a); //28
因為返回了對象,將這個對象作為返回值。
call/apply 方法與 this
在call/apply 方法中,this永遠指向它的第一個參數。如:
function add(c, d) {
return this.a + this.b + c + d;
}
var o = {
a: 1,
b: 3
};
add.call(o, 5, 7); // 1 + 3 + 5 + 7 = 16
add.apply(o, [10, 20]); // 1 + 3 + 10 + 20 = 34
在遇到this產生困惑的時候,建議先將其改寫成call/apply的形式,更方便判斷。