javascript
学JS的心路历程 -函式(三)this
this是什么,取決于被呼叫的呼叫地點。
?
昨天有提到說,呼叫函式時候會傳遞隱含參數(shù):arguments和this并講解了arguments,今天我們就來探討this吧!
?
什么是this
我們都會呼叫函式來使用,但有想過到底是從哪里呼叫到這個函式嗎?
this通常被稱作函式背景空間(function context),也就是說透過this我們可以知道到底是由誰呼叫這支函式(yjssqsdg)。我們無法在一開始定義它,只有函式呼叫時候才能確定。
?
函式的呼叫有四種方式:
?
作為函式呼叫
作為一個(物件)的方法呼叫
作為一個建構(gòu)式函式呼叫
透過apply、call呼叫
apply、call我們會在下一篇中介紹,我們今天主要介紹上述三種呼叫方式。
?
作為函式呼叫
function funA(){
console.log(this);
}
funA();//Window
由于是在全局環(huán)境呼叫funA,所以這時候的this就會是window。
?
所以很多剛學(xué)習(xí)的人都會遇到這個問題:
?
function funA(){
this.count ++;
}
funA.count = 0;
funA();
console.log(funA.count);//0
明明已經(jīng)聲明funA.count = 0怎么會沒有加到呢?這就是因為funA是被全局環(huán)境也就是window呼叫,所以this并不是你預(yù)期的funA。
?
那到底加了誰的count呢?你可以嘗試印出window.count會發(fā)現(xiàn)是NaN,是因為你賦予window一個count屬性且一開始沒有給定初始值,
所以會變成undefined+ 1 = NaN。
?
或許你認為這樣就可以解決問題:
?
function funA(val){
val.count ++;
}
var dart = {
count:0
};
funA(dart);
console.log(dart.count);//1
但這樣你只是在逃避this這個問題而已!!
要透過this解決方案有兩種,一個是等下提到的作為物件的方法;一個是明天會說的call及apply。
?
作為方法呼叫
函式可以透過寫在物件里面去呼叫,這個呼叫方式稱作作為方法(method),相信大家都知道,但你知道在這時候的this是什么嗎?
?
var obj = {
funA:function(){
console.log(this);
console.log(this===obj);
}
}
obj.funA();
//{funA:?}
//true
可以看到這時候的this是obj物件,也是是說我們是透過obj去呼叫的。
但是要注意一個小地方:
?
function funA(){
console.log(this);
console.log(this===obj);
}
var obj = {
a:funA
}
funA();
//Window
//false
雖然你認為我已經(jīng)讓obj參照funA了,但是當(dāng)你直接執(zhí)行funA時,還是由全局環(huán)境去呼叫,這也呼應(yīng)了我們開頭所說的「我們無法在一開始定義它,只有函式呼叫時候才能確定」。
?
我們可以利用作為方法呼叫來解決作為函式呼叫的問題:
?
function funA(){
this.count ++;
}
var obj = {
count:0,
sum:funA
};
obj.sum();
console.log(obj.count);//1
作為建構(gòu)式呼叫
建構(gòu)式的函式聲明就跟任何函式一樣,也可以用聲明和表達來建立新物件。
要作為建構(gòu)式函式來呼叫函式,必須要在函式呼叫前加上new:
?
function myConstructor(){
this.count = 0;
this.sum = function(){
return this.count ++
}
}
var a = new myConstructor();
a.sum();
console.log(a.count);
也許有人會覺得,這跟作為方法呼叫很像,那用物件去寫就好何必這么麻煩還要學(xué)建構(gòu)式,用奇怪的new去呼叫函式。
?
這邊就來說明一下,使用new呼叫函式時,會發(fā)生什么事:
?
建立一個新物件。
此物件被當(dāng)成this參數(shù)傳遞給建構(gòu)式,因此成為建構(gòu)式的函式背景空間(swrebar)。
回傳新建立的物件。
如果我們今天需要兩個相同的物件,如果用作為物件方法呼叫的話就必須建立兩個不同的物件,否則會參照到同樣的物件并修改。
但是建構(gòu)式就不需要,因為每一個都是一個新的物件:
?
function myConstructor(){
this.count = 0;
this.sum = function(){
return this.count ++
}
}
var a = new myConstructor();
var b = new myConstructor();
a.sum();
console.log(b.count);//0
以上就是this的基本三種呼叫方式,若有錯誤及參考資料未附上勞請留言。
明天我們會介紹this的稍微進階應(yīng)用call及apply。
?
參考資料:
忍者JavaScript開發(fā)技巧探秘
你所不知道的JS - this
徹底理解js中this的指向,不必硬背。
轉(zhuǎn)載于:https://www.cnblogs.com/lannyQ-Q/p/9935901.html
總結(jié)
以上是生活随笔為你收集整理的学JS的心路历程 -函式(三)this的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: Ubantu使用笔记
- 下一篇: 苏宁大促高并发要求下的售后服务运营能力承