国产xxxx99真实实拍_久久不雅视频_高清韩国a级特黄毛片_嗯老师别我我受不了了小说

資訊專欄INFORMATION COLUMN

JavaScript中this終極理解(1)

YacaToy / 2599人閱讀

摘要:關(guān)鍵字是中一個復(fù)雜的機制,它被自動定義在所有的函數(shù)作用域中。指向它自身匿名函數(shù)無法指向自身第一個函數(shù)被稱為具名函數(shù),在它內(nèi)部可以使用來引用自身。的綁定和函數(shù)聲明的位置沒有任何關(guān)系,取決于函數(shù)的調(diào)用方式。這是理解的前提。

this關(guān)鍵字是JavaScript中一個復(fù)雜的機制,它被自動定義在所有的函數(shù)作用域中。

1. 為什么要用this
function identify() {
    return this.name.toUpperCase()
}

function speak() {
    var greeting = "hello, i"am" + identify.call(this)
    console.log(greeting)
}

var me = {
    name: "Kyle"
}
var you = {
    name: "Reader"
}

identify.call(me); //KYLE
identify.call(you) //READER

speak.call(me) //Hello, 我是KYLE
speak.call(you) //Hello, 我是READER

上面這部分代碼在不同的上下文對象中重復(fù)使用identify()和speak(),不用針對每個對象編寫不同版本的函數(shù)。
如果不使用this,那就需要給identify()和speak()顯示傳入一個上下文對象

function identify(context) {
    return context.name.toUpperCase();
}
function speak(context) {
    var greeting = "Hello i"am" + identify(context)
    console.log(greeting)
}
identify(you) //READER
speak(me) //hello, 我是KYLE

然而,this提供了一種更優(yōu)雅的方式來隱式傳遞一個對象引用,因此可以將API設(shè)計的更加簡潔且易于復(fù)用。
當(dāng)你的代碼越來越復(fù)雜的時候,顯示的傳遞上下文對象會變得很混亂。

2. 關(guān)于this的誤解之 誤解之this是指向自身

通常會將this理解成指向函數(shù)自身。平常我們會在函數(shù)內(nèi)部調(diào)用自身(例如遞歸)。在JavaScript中函數(shù)也是一個對象,那么我們可以在調(diào)用函數(shù)的時候存儲狀態(tài)(屬性的值)。
我們看下以下代碼,會發(fā)現(xiàn)this并沒有指向函數(shù)本身:

//記錄foo的調(diào)用次數(shù)
function foo(num) {
    console.log("foo: "+ num)
    this.count ++ 
}
foo.count = 0;
var i;
for(i=0; i<10; i++) {
    if(i>5) {
        foo(i)
    }
}

//foo: 6
//foo: 7
//foo: 8
//foo: 9
//foo 被調(diào)用了多少次?
console.log(foo.count) //0

可以看到foo()執(zhí)行了4次,但是foo.count仍然是0,所以從字面上理解this指向的是當(dāng)前函數(shù)自身就是錯誤的!
在執(zhí)行foo.count=0的時候,確實向函數(shù)對象foo添加了一個count屬性,但是函數(shù)內(nèi)部的this.count的this并不是指向那個函數(shù)對象(其實是window對象)。
那么增加的是哪個count?這是創(chuàng)建在全局變量的一個count,值為NaN.

如果要從函數(shù)對象內(nèi)部引用它自身,那只使用this是不夠的。一般你需要通過一個指向函數(shù)對象的詞法標(biāo)識符來引用。

function foo() {
    foo.count = 4    //foo指向它自身
}
setTimeout(function() {
    //匿名函數(shù)無法指向自身
}, 10)

第一個函數(shù)被稱為具名函數(shù),在它內(nèi)部可以使用foo來引用自身。但是在第二個例子中,傳入setTimeout(..)的回調(diào)函數(shù)沒有名稱標(biāo)識符,因此無法從函數(shù)內(nèi)部引用自身。

還有一種方法是通過強制this指向foo函數(shù)對象

function foo(num) {
    console.log("foo:" + num)
    this.count ++
}
foo.count = 0
var i;
for(i=0; i<10; i++) {
    if(i>5) {
        foo.call(foo, i)
    }
}

如上,我們強制this指向了foo,這樣就可以獲得我們想要的答案了。

誤解之它的作用域

第二種錯誤的理解是this指向函數(shù)的作用域。這個問題有些復(fù)雜,因為在某種情況下它是正確的。
需要明確的是,this在任何情況下都不指向函數(shù)的詞法作用域。在JavaScript內(nèi)部,作用域確實很像對象,可見的標(biāo)識符都是它的屬性。但是作用域?qū)ο笫菬o法通過JavaScript代碼進(jìn)行訪問,它是在JavaScript引擎內(nèi)部。

function foo() {
    var a = 2;
    this.bar();
}

function bar() {
    console.log(this.a)
}

foo(); // a is not defined

以上代碼運行是不會得到你理想的結(jié)果的,因為你不能使用this來引用一個詞法作用域內(nèi)部的東西。

3. this到底是什么

this是在運行時進(jìn)行綁定的,并不是在編寫時綁定,它的上下文取決于函數(shù)調(diào)用時的各種條件。this的綁定和函數(shù)聲明的位置沒有任何關(guān)系,取決于函數(shù)的調(diào)用方式。

當(dāng)一個函數(shù)調(diào)用時,會創(chuàng)建一個活動記錄(有時候也稱為執(zhí)行上下文)。這個記錄 會包含函數(shù)在哪里被調(diào)用(調(diào)用棧),函數(shù)的調(diào)用方法,傳入的參數(shù)信息。this就是記錄的其中一個屬性,會在函數(shù)執(zhí)行的過程中用到。

總結(jié)

這里我們要明白this既不是指向函數(shù)自身,也不是指向函數(shù)的詞法作用域。這是理解this的前提。
this實際上時在函數(shù)被調(diào)用時發(fā)生的綁定,它指向什么完全取決于函數(shù)在哪里被調(diào)用。

文章版權(quán)歸作者所有,未經(jīng)允許請勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。

轉(zhuǎn)載請注明本文地址:http://specialneedsforspecialkids.com/yun/89948.html

相關(guān)文章

  • JavaScriptthis終極理解(2)

    摘要:找到函數(shù)的調(diào)用位置最重要的是要分析調(diào)用棧就是為了到達(dá)當(dāng)前執(zhí)行位置所調(diào)用的所有函數(shù)。顯示綁定我們可以使用函數(shù)的和方法,通過這兩個方法可以在某個對象上強制調(diào)用函數(shù)。 在上一篇我們了解過每個函數(shù)的this是在調(diào)用的時候綁定的,完全卻決于函數(shù)的調(diào)用位置(也就是函數(shù)的調(diào)用方法)。 1. 調(diào)用位置 在理解this的綁定過程之前,首先要理解調(diào)用位置:調(diào)用位置就是函數(shù)在代碼中被調(diào)用的位置,而不是聲明的...

    liujs 評論0 收藏0
  • 筆試題之Event Loop終極

    摘要:下面開始分析開頭的代碼第一輪事件循環(huán)流程整體作為第一個宏任務(wù)進(jìn)入主線程,遇到,輸出遇到函數(shù)聲明,聲明暫時不用管遇到,其回調(diào)函數(shù)被分發(fā)到微任務(wù)中。我們記為遇到,其回調(diào)函數(shù)被分發(fā)到宏任務(wù)中。 先上一道常見的筆試題 console.log(1); async function async1() { console.log(2); await async2(); con...

    niceforbear 評論0 收藏0
  • 面試題之Event Loop終極

    摘要:下面開始分析開頭的代碼第一輪事件循環(huán)流程整體作為第一個宏任務(wù)進(jìn)入主線程,遇到,輸出遇到函數(shù)聲明,聲明暫時不用管遇到,其回調(diào)函數(shù)被分發(fā)到微任務(wù)中。我們記為遇到,其回調(diào)函數(shù)被分發(fā)到宏任務(wù)中。 先上一道常見的筆試題 console.log(1); async function async1() { console.log(2); await async2(); con...

    233jl 評論0 收藏0
  • jsthis的“終極三問”

    摘要:是什么本質(zhì)是一個綁定,在函數(shù)被調(diào)用時建立。它的指向是完全由函數(shù)被調(diào)用的調(diào)用點來決定的。因為函數(shù)的調(diào)用點在全局作用域,所以指向全局變量這里就是函數(shù)的調(diào)用點存在的意義在函數(shù)體內(nèi)部指代函數(shù)當(dāng)前的運行環(huán)境。從而實現(xiàn)干凈的設(shè)計和更容易的復(fù)用。 this是什么? this 本質(zhì)是一個綁定, 在函數(shù)被調(diào)用時建立。它的指向是完全由函數(shù)被調(diào)用的調(diào)用點來決定的。 function baz() { ...

    silvertheo 評論0 收藏0
  • 終極蛇皮上帝視角之微信小程序之告別 setData

    摘要:而小程序官方的是在中調(diào)用方法來改變數(shù)據(jù),從而改變界面。為了寫測試讓咱們來重構(gòu)一把,利用學(xué)習(xí)過的函數(shù)式編程中的高階函數(shù)把依賴注入。也就是說當(dāng)中的某個數(shù)據(jù)更新的時候,我們并不知道它會影響哪個中的屬性,特別的還有依賴于的情況。 眾所周知 Vue 是借助 ES5 的 Object.defineProperty 方法設(shè)置 getter、setter 達(dá)到數(shù)據(jù)驅(qū)動界面,當(dāng)然其中還有模板編譯等等其他...

    wuyumin 評論0 收藏0

發(fā)表評論

0條評論

最新活動
閱讀需要支付1元查看
<