五月综合缴情婷婷六月,色94色欧美sute亚洲线路二,日韩制服国产精品一区,色噜噜一区二区三区,香港三级午夜理伦三级三

您現(xiàn)在的位置: 365建站網(wǎng) > 365文章 > JavaScript中的[[scope]]和Scope Chain

JavaScript中的[[scope]]和Scope Chain

文章來源:365jz.com     點(diǎn)擊數(shù):309    更新時(shí)間:2009-09-30 11:59   參與評(píng)論
主機(jī)網(wǎng)全新上線,買空間、服務(wù)器就上主機(jī)網(wǎng),安全有保障!CNIDC.COM

ECMA262中規(guī)定JS使用Scope Chain來實(shí)現(xiàn)closure,Scope Chain是JS中非常重要的機(jī)制,JS中所有的標(biāo)識(shí)符(Identifier)都是通過Scope Chain來查找值的。下面的部分是關(guān)于ECMA262及其實(shí)現(xiàn)SpiderMonkey和JScript如何用Scope Chain和[[scope]]來實(shí)現(xiàn)closure的。

變量標(biāo)識(shí)符查找

當(dāng)我們?cè)贘S程序里寫下像a++這樣的表達(dá)式時(shí),很難想象a的值和內(nèi)存地址經(jīng)過了復(fù)雜的查找過程才得以確定,JS的所有標(biāo)識(shí)符(通常是我們自己定義的變量名)在執(zhí)行時(shí)都是從Scope Chain中查找值的,這也是導(dǎo)致JS執(zhí)行速度低的原因和JS實(shí)現(xiàn)靈活的動(dòng)態(tài)特性的基礎(chǔ)。Scope Chain是一個(gè)鏈表,在JS執(zhí)行時(shí),總是維護(hù)著Scope Chain來保證變量的可訪問性或者不可訪問性。對(duì)于這個(gè)過程ECMA262給出了很明確的描述(我翻譯了一下,各位將就著看):

1. 獲取Scope Chain的下一個(gè)對(duì)象。如果沒有對(duì)象了,則轉(zhuǎn)到第5步。

2. 調(diào)用結(jié)果(1)的[[HasProperty]]方法, 傳遞Identifier作為參數(shù)

3. 如果結(jié)果(2)是true, Reference(引用)類型的值,它的base object是結(jié)果(1)而它的

property name是Identifier

4. 跳到第1步

5. 返回一個(gè)Reference類型,它的base object是null它的property name 是Identifier.

注:Reference(引用)類型的值是JS引擎使用的一種數(shù)據(jù)類型,它分為base object和property  name兩個(gè)部分。假設(shè)在JS代碼中有obj.prop這樣的表達(dá)式,那么解釋成Reference類型,base object是對(duì)象obj,而property name是字符串”prop”

Scope Chain開始時(shí)被設(shè)為宿主對(duì)象,所以在全局代碼中的變量就是宿主對(duì)象的屬性。Scope Chain在執(zhí)行時(shí)由JS引擎自動(dòng)維護(hù),編譯型的引擎也會(huì)創(chuàng)建相應(yīng)的運(yùn)行時(shí)環(huán)境來做此事。Scope Chain一般在函數(shù)調(diào)用或者執(zhí)行進(jìn)入with塊的時(shí)候改變。

函數(shù)的執(zhí)行

JS函數(shù)執(zhí)行并非簡(jiǎn)單地執(zhí)行函數(shù)體(Function Body)中的JS代碼,在此之前JS引擎會(huì)創(chuàng)建一個(gè)Activation Object,這個(gè)對(duì)象將會(huì)被作為Scope Chain的頂端,而函數(shù)的[[scope]]屬性中的對(duì)象將被鏈接為其后續(xù)的對(duì)象。([[scope]]在函數(shù)定義時(shí)被確定,稍后的內(nèi)容是關(guān)于[[scope]]如何定義的。)這意味著Function Body中的JS代碼所使用的標(biāo)識(shí)符都是按照上一部分所描述的,最先從Activation Object開始查找的。Activation Object創(chuàng)建時(shí)只有一個(gè)arguments屬性,它不會(huì)繼承Object.prototype的屬性和方法。接下來的變量初始化(Variable Instantiation)將函數(shù)體中變量和函數(shù)聲明的結(jié)果添加到Activation Object作為屬性。

函數(shù)的[[scope]]屬性

[[scope]]是ECMA262規(guī)定的對(duì)象的私有屬性,理論上只有JS引擎可以訪問,但FireFox的幾個(gè)引擎(SpiderMonkey和Rhino)提供了私有屬性__parent__來訪問它(所以一會(huì)我們可以看一看它)。盡管所有對(duì)象都有[[Scope]]但是它只對(duì)函數(shù)對(duì)象有用。

對(duì)于函數(shù)聲明和匿名函數(shù)表達(dá)式來說,[[scope]]就是它創(chuàng)建時(shí)的Scope Chain,但是對(duì)于有名字的函數(shù)表達(dá)式,[[scope]]頂端是一個(gè)新的JS對(duì)象(也就是繼承了Object.prototype),這個(gè)對(duì)象被鏈到函數(shù)創(chuàng)建時(shí)的Scope Chain,它本身有一個(gè)屬性就是函數(shù)的名字,這確保了函數(shù)內(nèi)部的代碼可以無誤地訪問自己的函數(shù)名進(jìn)行遞歸。

舉個(gè)例子

以下為引用的內(nèi)容:

function f1()
{
    return n>1?n*f1(n-1):1;
}

var f2=function f()
{
    return n>1?n*f(n-1):1;
}

f1的遞歸是不安全的,而f2的遞歸是安全的。但是注意這僅僅是針對(duì)標(biāo)準(zhǔn)的規(guī)定而言,事實(shí)上IE并沒有實(shí)現(xiàn)這個(gè)性質(zhì)。

如對(duì)本文有疑問,請(qǐng)?zhí)峤坏浇涣髡搲?,廣大熱心網(wǎng)友會(huì)為你解答!! 點(diǎn)擊進(jìn)入論壇

發(fā)表評(píng)論 (309人查看,0條評(píng)論)
請(qǐng)自覺遵守互聯(lián)網(wǎng)相關(guān)的政策法規(guī),嚴(yán)禁發(fā)布色情、暴力、反動(dòng)的言論。
昵稱:
最新評(píng)論
------分隔線----------------------------

其它欄目

· 建站教程
· 365學(xué)習(xí)

業(yè)務(wù)咨詢

· 技術(shù)支持
· 服務(wù)時(shí)間:9:00-18:00
365建站網(wǎng)二維碼

Powered by 365建站網(wǎng) RSS地圖 HTML地圖

copyright © 2013-2024 版權(quán)所有 鄂ICP備17013400號(hào)