js中this的指向問題總結(精華版)
阿新 • • 發佈:2020-08-12
js中this的指向問題總結
1.全域性的this和普通函式中的this
- ES5非嚴格模式 全域性中this和普通函式中this都指向window
- ES5嚴格模式,ES6,全域性中this仍然指向window,普通函式中this指向undefined
ES5非嚴格模式
console.log(this); //window
function fn(){
console.log(this); //window
}
fn();
ES5嚴格模式 ES6
"use strict"; console.log(this); //window function fn(){ console.log(this); //undefined } fn();
2.物件中的this
- 物件方法中的this指向此物件,直接this指向物件外this的指向
var obj={
a:1,
b:function(){
console.log(this); // this指向當前物件自身obj
},
c:this.a // this指向物件外this的指向
}
3.回撥函式中的this 3種情況
- 如果直接指向的回撥函式,this指向最外層window
- 如果通過arguments直接使用引數指向函式,this則指向執行當前函式的arguments
- 如果回撥函式通過call,apply,bind重新指向了新的物件時,this就是指向新物件
var obj = { a: function () { console.log(this,"____"); var self=this; function fn1(fn) { console.log(this)//物件方法內的函式相當普通函式的執行 指向window fn(); // arguments[0](); //arguments // fn.call(self); //obj } function fn2() { console.log(this);//window 回撥函式中 } fn1(fn2); }, }; obj.a();
var obj={
b:1,
a:function(){
setTimeout(function(){
console.log(this); //window 儘管在setTimeout中,但是依舊是回撥函式中的this指向
}, 2000);
setTimeout(function(obj){
console.log(this) //window 回撥函式
console.log(obj); //obj 這個是外部傳參,this作為引數傳進來.this指向的是obj
}, 2000,this);
}
}
obj.a();
4.事件中的this
var obj={
b:1,
a:function(){
// console.log(this);
// 特殊的回撥函式
document.addEventListener("click",this.clickHandler);
// document.attachEvent("onclick",this.clickHandler);
},
clickHandler:function(e){
console.log(this===document);//addEventListener事件偵聽的物件 e.currentTarget
// console.log(this===window);//IE8 attachEvent偵聽事件時,this指向window
}
}
obj.a();
5.ES6類中的this
- 任何的靜態方法中this都是當前類,也是建構函式
- 靜態方法中無法獲取到例項化物件的this的
class Box{
static _instance;
constructor(){
console.log(this);//指向被例項化的物件
}
static getInstance(){ //單例模式
if(!Box._instance){
Box._instance=new Box();
}
return Box._instance;
}
play(){
console.log(this,"|");//指向被例項化的物件
}
static run(){
// console.log(this);
console.log(this===Box,"____");
return this;
}
static plays(){
this.getInstance().play();
var o=this.getInstance(); //單例模式的效果,獲得的例項化都相同
var o1=this.getInstance();
console.log(o===o1);
}
}
var b=new Box();//會執行建構函式,這是建構函式中this就是這個b物件
b.play();//b物件下的方法play,因此play方法中this被指向b,誰執行play,this指向誰
console.log(Box.run()===b);//false
console.log(Box.run()===b.constructor);//true
6.ES5 面向物件中的this
function Box(){
console.log(this);
}
Box.prototype.play=function(){ //相當於ES6中類中的動態方法中的this
console.log(this);//this是指向執行該方法的例項化物件
}
Box.run=function(){ //相當於ES6中類中的靜態方法中的this
console.log(this);//Box
}
Box();//this是window或者undefined
var b=new Box();// this是例項化後b物件
b.play();
7.箭頭函式
var obj = {
a: function () {
setTimeout(() => {
console.log(this);//this是箭頭函式外this的指向 所以this指向obj
// 上下文環境中this的指向
}, 2000);
},
};
obj.a();
8.繫結this指向
call apply bind
function fn(){
console.log(this);
}
var obj={a:1}
fn.call(obj);//fn中this指向obj
fn.apply(obj);//fn中this 指向obj
fn.bind(obj)();//fn中this指向obj