1,執(zhí)行環(huán)境(executioncontext)是javascript中非常重要的一個(gè)概念。執(zhí)行環(huán)境定義了變量或函數(shù)有權(quán)訪問的其他數(shù)據(jù),決定了它們各自的行為。每個(gè)執(zhí)行環(huán)境都有一個(gè)與之關(guān)聯(lián)的變量對象到千,環(huán)境中定義的所有變量和函數(shù)都保存在這個(gè)對象中,雖然我們編寫的代碼無法訪問這個(gè)對象赴穗,但是解析器在處理數(shù)據(jù)時(shí)會在后臺使用它憔四。
2,全局執(zhí)行環(huán)境是最外圍的一個(gè)執(zhí)行環(huán)境般眉。根據(jù)js所在的宿主環(huán)境不同了赵,表示執(zhí)行環(huán)境的對象也不一樣。在web瀏覽器中甸赃,全局執(zhí)行環(huán)境被認(rèn)為是window對象柿汛,因此所有全局變量和函數(shù)都是作為window對象的屬性和方法來創(chuàng)建的。某個(gè)執(zhí)行環(huán)境中的所有代碼執(zhí)行完畢后埠对,該環(huán)境唄銷毀络断,保存在其中的所有變量和函數(shù)定義也隨之被銷毀(全局執(zhí)行環(huán)境知道應(yīng)用程序退出裁替,例如關(guān)閉網(wǎng)頁或者瀏覽器時(shí)才會被銷毀)。
3貌笨,每個(gè)函數(shù)都有自己的執(zhí)行環(huán)境胯究。當(dāng)執(zhí)行流進(jìn)入一個(gè)函數(shù)時(shí),函數(shù)的環(huán)境就會被推入一個(gè)環(huán)境棧中躁绸。而在函數(shù)執(zhí)行之后,棧將其環(huán)境彈出臣嚣,把控制權(quán)返回給之前的執(zhí)行環(huán)境净刮。js程序中的執(zhí)行流正是由這個(gè)機(jī)制控制的。
4硅则,當(dāng)代碼在一個(gè)環(huán)境中執(zhí)行時(shí)淹父,會創(chuàng)建變量對象的一個(gè)作用域鏈(scopechain)。作用域鏈的用途怎虫,是保證對執(zhí)行環(huán)境有權(quán)訪問的所有變量和函數(shù)的有序訪問暑认。作用域鏈的前端,始終都是當(dāng)前執(zhí)行的代碼所在環(huán)境的變量對象大审。如果這個(gè)環(huán)境是函數(shù)蘸际,則將其活動對象自以為變量對象⊥椒觯活動對象在最開始時(shí)只包含一個(gè)變量粮彤,即arguments對象(該對象在全局環(huán)境中是不存在的)。作用域鏈中的下一個(gè)變量對象來自包含(外部)環(huán)境姜骡,而再下一個(gè)變量對象則來自下一個(gè)包含環(huán)境导坟。這樣,一直延續(xù)到全局環(huán)境圈澈,全局環(huán)境的變量對象始終是作用域鏈中的最后一個(gè)對象惫周。
5,在作用域鏈中康栈,內(nèi)部環(huán)境可以通過作用域鏈來訪問所有的外部環(huán)境递递,但是外部環(huán)境不能訪問內(nèi)部環(huán)境中的任何變量和函數(shù)。
6谅将,使用var聲明的變量會自動被添加到最接近的環(huán)境中漾狼。在函數(shù)內(nèi)部,最接近的環(huán)境就是函數(shù)的局部環(huán)境饥臂;如果初始化變量時(shí)沒有使用var聲明逊躁,該變量會自動被添加到全局環(huán)境。
7隅熙,訪問局部變量要比訪問全局變量更快稽煤,因?yàn)椴挥孟蛏纤阉髯饔糜蜴湣?/p>
本節(jié)源碼下載地址:JavaScript學(xué)習(xí)筆記(6):執(zhí)行環(huán)境和作用域