【ES6】兩個例子明白箭頭函數this指向

前言:es6箭頭函數沒出現之前,this的指向不是函數被創建時綁定,而是被怎麼樣的方式調用時綁定的。而箭頭函數剛好相反,箭頭函數的this指向是函數被創建時綁定的,它的指向就是當前詞法作用域中的this,並且不會因爲被怎麼樣的方式調用改變綁定。

如果對非箭頭函數this指向有問題的朋友,建議看我之前的文章。【JavaScript】this的指向詳解

(爲了展示方便,這兩個例子都是在瀏覽器環境中運行,所以全局對象是window)

一、例子①

//這裏只能用var定義變量,let,const定義的變量,不是綁定在window下。
var str = 'window';  
 
const obj = {
    str:'obj',
    nativeFn: function(){
	console.log(this.str, '當前詞法作用域中的this');
	return function(){
	    console.log('原生函數',this.str);	
	}
    },
    arrowFn: function(){
	console.log(this.str, '當前詞法作用域中的this');
	return ()=>{
	    console.log('箭頭函數',this.str);	
	}
    }
};
const obj2 = {
    str:'obj2'	
}
 
var nativeFn = obj.nativeFn();
var arrowFn = obj.arrowFn();
	
console.log('函數調用一 **********');  
nativeFn();
arrowFn();  
	
console.log('函數調用二 **********');  
nativeFn.call(obj2);
arrowFn.call(obj2);    
	
console.log('函數調用三 **********'); 
setTimeout(function(){    
    nativeFn();
    arrowFn();	
},50);
 
//函數調用四
var doc = document.documentElement;
doc.str = 'document';
doc.addEventListener('click',function(){
    console.log('函數調用四 **********'); 
},false);
doc.addEventListener('click',nativeFn,false);
doc.addEventListener('click',arrowFn,false);

運行結果

通過運行結果可以發現, 無論我們怎麼改變箭頭函數arrowFn的調用方式,都不會改變this的指向,this始終指向它被創建時所處的詞法作用域中的this。

 

二、例子②

//這裏只能用var定義變量,let,const定義的變量,不是綁定在window下。
var str = 'window';  
 
const obj = {
    str:'obj',
    fn: ()=>{
	console.log(this.str);	
    }
}

obj.fn();

運行結果

這時候this竟然指向了window對象,這也是使很多剛接觸箭頭函數的朋友容易困惑的一個點。在看看下面的例子相信就能理解這個問題的原因了。

//這裏只能用var定義變量,let,const定義的變量,不是綁定在window下。
var str = 'window';  
 
const obj = {
    str:'obj',
    fn: ()=>{
	console.log(this.str);	
    },
    fn2: function(){
	console.log(this.str, '當前詞法作用域中的this')
	return {
	    str: 'newObj',
	    fn: ()=>{
		console.log(this.str);	
	    }	
	}
    }
}

obj.newFn = ()=>{
    console.log(this.str);	
}

obj.fn();
obj.newFn();

var newObj = obj.fn2();
newObj.fn();

運行結果

這裏已經不難看出來了,當我們創建對象的時候,是在全局作用域下創建的,而對象中的方法也是這時候創建的

(參照obj.newFn),

所以這時候的this是指向全局的,而我們在fn2裏面創建的對象,這個對象的方法的this就指向他被創建時的詞法作用域obj了。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章