function? 普通執(zhí)行? this指向的是window
而new的時(shí)候 ? ?this ?是指向這個(gè)實(shí)例的
要不停的看基礎(chǔ)才行。 ?不停的看 ?不停的看
這里需要說(shuō)下 ?call ?和apply ? ?當(dāng)你做某個(gè)應(yīng)用時(shí)玉组,需要把一個(gè)function中的this ?綁定到一個(gè) ?具體的Object上面溯饵,來(lái)執(zhí)行這個(gè)funciton喉悴,那么你該怎么做?
function lei(){
? ? ?alert(this.name.toUpperCase())
}
var test = {
? ?name:'dinglei'
}
lei.call(test) //DINGLEI
隨著你的使用模式越來(lái)越復(fù)雜,顯式傳遞上下文對(duì)象會(huì)讓代碼變得越來(lái)越混亂治唤,使用 this 則不會(huì)這樣--《你不知道的JavaScript》
巨大的需要注意的地方:this是在運(yùn)行時(shí)進(jìn)行綁定的,并不是編寫時(shí)幫綁定的糙申。它的具體指向宾添,是你當(dāng)時(shí)如何運(yùn)行這個(gè)函數(shù)決定的。
普通執(zhí)行
function test (){console this.a}
對(duì)象綁定
obj = {name:test,a:'ddd'} ? obj.name()
隱試綁定和顯示綁定柜裸。缕陕。 ? ? ?最后還有個(gè)顯示變種硬綁定。
Function.prototype.bind ?就是硬綁定疙挺。扛邑。 ? ? ?返回的是一個(gè)已經(jīng)綁定死this的函數(shù)。铐然。蔬崩。 ? ?啦啦啦啦啦啦啦
那么這是怎么實(shí)現(xiàn)的? ?其實(shí)bind ?就是返回個(gè)函數(shù) ?而這個(gè)函數(shù)里面是 ?apply在干活搀暑, ? 所以一直只能是 ?綁定的那個(gè)obj在那里哦
// 簡(jiǎn)單的輔助綁定函數(shù)
function bind(fn, obj) {
? return function() {
? ? ?return fn.apply( obj, arguments );
? };
}
new ?綁定
最后做個(gè)總結(jié):如何識(shí)別this的綁定
判斷 this
現(xiàn)在我們可以根據(jù)優(yōu)先級(jí)來(lái)判斷函數(shù)在某個(gè)調(diào)用位置應(yīng)用的是哪條規(guī)則沥阳。可以按照下面的
順序來(lái)進(jìn)行判斷:
1. 函數(shù)是否在 new 中調(diào)用( new 綁定)自点?如果是的話 this 綁定的是新創(chuàng)建的對(duì)象桐罕。
var bar = new foo()
2. 函數(shù)是否通過(guò) call 、 apply (顯式綁定)或者硬綁定調(diào)用?如果是的話功炮, this 綁定的是
指定的對(duì)象溅潜。
var bar = foo.call(obj2)
3. 函數(shù)是否在某個(gè)上下文對(duì)象中調(diào)用(隱式綁定)?如果是的話死宣, this 綁定的是那個(gè)上
下文對(duì)象伟恶。
var bar = obj1.foo()
4. 如果都不是的話,使用默認(rèn)綁定毅该。如果在嚴(yán)格模式下博秫,就綁定到 undefined ,否則綁定到
全局對(duì)象眶掌。
var bar = foo()
就是這樣挡育。對(duì)于正常的函數(shù)調(diào)用來(lái)說(shuō),理解了這些知識(shí)你就可以明白 this 的綁定原理了朴爬。
不過(guò)……凡事總有例外
this 綁定的應(yīng)用:
1.函數(shù)參數(shù)柯里化
function foo(a,b) {
? ? console.log( "a:" + a + ", b:" + b );
}
// 把數(shù)組“展開(kāi)”成參數(shù)
foo.apply( null, [2, 3] ); // a:2, b:3
// 使用 bind(..) 進(jìn)行柯里化
var bar = foo.bind( null, 2 );
bar( 3 ); // a:2, b:3