摘要:五階段運(yùn)行結(jié)果運(yùn)行結(jié)果原因在運(yùn)行前,我就猜想彈出的這個(gè)應(yīng)該是一個(gè)的可沒(méi)想到卻是,這使我百思不得其解。當(dāng)我們程序真正運(yùn)行時(shí),我們把參數(shù)傳過(guò)去,在這里并不會(huì)把這個(gè)參數(shù)值賦值給這個(gè)形參。
要寫出嚴(yán)謹(jǐn)?shù)拇a或者是優(yōu)化性能就必須做到‘知己知彼’,為此把握事物規(guī)律方能有備無(wú)患,穩(wěn)步前進(jìn),故對(duì)此有所探知。
一、階段var a = 5; function f(n){ alert(a); } f();
上面代碼的全局處理過(guò)程:
1、預(yù)處理階段
a、讀取分析整個(gè)源代碼 b、先掃描函數(shù)聲明,之后掃描變量(var聲明) b_a、處理**函數(shù)聲明**時(shí)有沖突,會(huì)覆蓋 b_b、處理變量聲明時(shí)有沖突,會(huì)忽略(相對(duì)函數(shù)聲明) c、將掃描到的函數(shù)和變量保存到一個(gè)對(duì)象中(全局的保存到window對(duì)象中) d、變量的值是undefined,函數(shù)的值則指向該函數(shù)(是一個(gè)函數(shù)字符串) 形式如下:{a : undefined, f : "function(){alert(a);}"}
2、運(yùn)行階段
在我們剛剛的案例中 a、將變量a的值從undefined改為5 b、調(diào)用f(),一遍函數(shù)得到執(zhí)行
上面函數(shù)代碼的處理過(guò)程:
**1、預(yù)處理階段** a、將函數(shù)的參數(shù)添加到一個(gè)對(duì)象(**詞法對(duì)象**) b、掃描**函數(shù)聲明**,之后掃描變量(var聲明) d、將掃描到的函數(shù)和方法添加到詞法對(duì)象里面 c、變量的值是undefined,函數(shù)的值則指向該函數(shù)(與全局的一樣) 2、運(yùn)行階段 與全局的的運(yùn)行原理一樣二、階段
var b = 1; function ff(){ alert(b); var b = 5; alert(b); } ff(); //結(jié)果彈出為:undefined
原因:
js在預(yù)處理階段時(shí),將函數(shù)ff()和變量b保存到window對(duì)象中,
此時(shí)b = undefined,到了運(yùn)行階段,b = 1,這時(shí)調(diào)用函數(shù)ff(),
js會(huì)先把函數(shù)內(nèi)的變量添加到詞法對(duì)象中,此時(shí)b = undefined,
再之后alert(b),因?yàn)槭窃诜椒▋?nèi)部,所以alert(b)會(huì)調(diào)用詞法
對(duì)象中的b。然而這時(shí)詞法對(duì)象中的b = undefined,所以執(zhí)行結(jié)
果彈出的是undefined,當(dāng)alert執(zhí)行完之后b = 5;
三、階段alert(a); function a() { console.log("xx"); } var a = 5; function a() { console.log("yy"); } //運(yùn)行結(jié)果:"function a() { console.log("yy"); }"
原因:
我們發(fā)現(xiàn)變量a和兩個(gè)方法a()同名了,這時(shí),js在預(yù)處理的時(shí)候
會(huì)優(yōu)先將函數(shù)保存到window對(duì)象中,然后如果發(fā)現(xiàn)同名的是
變量,這時(shí)它會(huì)忽略這個(gè)變量;如果發(fā)現(xiàn)同名的是函數(shù),那
么后面的會(huì)將前面的覆蓋。所以執(zhí)行alert彈出的會(huì)是函數(shù)
四、階段alert(b); var b = 5; var b = function () { console.log("xx"); } //運(yùn)行結(jié)果:undefined
原因:
我們知道,定義一個(gè)方法有多種形式。像上面這個(gè)案例中,
我們的函數(shù)是匿名的,然后賦值給了一個(gè)變量。但變量終究
是變量,js不會(huì)因?yàn)樗闹当容^特別就特殊對(duì)待,所以,在
js在預(yù)處理的時(shí)候,先將第一個(gè)變量b保存到window中,此時(shí)
變量b=undefined,然后第二個(gè)變量b覆蓋了第一個(gè)變量,此時(shí)
的變量b依然還是等于undefined,所以在程序運(yùn)行的時(shí)候彈出
值會(huì)等于undefined。
五、階段function c(num1){ alert(num1); } c(2); //運(yùn)行結(jié)果:2 function d(num2){ alert(num2); var num2 = 5; } d(2); //運(yùn)行結(jié)果:2
原因:
在運(yùn)行前,我就猜想彈出的這個(gè)應(yīng)該是一個(gè)undefined的
可沒(méi)想到卻是2,這使我百思不得其解。
在js預(yù)處理的時(shí)候讀取到了這個(gè)函數(shù)有一個(gè)參數(shù),于是就
直接將這個(gè)參數(shù)放到了詞法對(duì)象中,這時(shí)個(gè)參數(shù)的值是
undefined,之后它繼續(xù)向下掃描,發(fā)現(xiàn)有一個(gè)變量定義,
但我們卻發(fā)現(xiàn)這變量與參數(shù)同名,這個(gè)時(shí)候js會(huì)怎么做?
這時(shí)按照之前所學(xué)的,這個(gè)變量會(huì)被加到詞法對(duì)象中,而
事實(shí)上也的確是加了,不過(guò)卻給它打上了一個(gè)標(biāo)簽,用來(lái)
標(biāo)識(shí)這個(gè)變量是一個(gè)參數(shù),這時(shí)這個(gè)變量的值也是undefined。
當(dāng)程序真正運(yùn)行的時(shí)候,我們把參數(shù)傳過(guò)去,這個(gè)參數(shù)就會(huì)賦值的到這個(gè)參數(shù)中,
然后彈出結(jié)果,然后再賦值為5。
六、階段接下來(lái)還有幾個(gè)問(wèn)題
1.看下面代碼
funciton f(num){ alert(num); funciton num(){ } } f(6);
返回結(jié)果為:"funciton num(){}"
像出現(xiàn)上面這個(gè)情況的時(shí)候,js也還是一樣在預(yù)處理的時(shí)
候,將參數(shù)放到詞法對(duì)象中,然后發(fā)現(xiàn)里面有一個(gè)同名的
函數(shù),這時(shí)js就會(huì)把這個(gè)函數(shù)放到詞法對(duì)象中,并覆蓋之
前的參數(shù),而它的值指向的就是這個(gè)函數(shù)。當(dāng)我們程序真
正運(yùn)行時(shí),我們把參數(shù)傳過(guò)去,js在這里并不會(huì)把6這個(gè)參
數(shù)值賦值給這個(gè)形參。
文章版權(quán)歸作者所有,未經(jīng)允許請(qǐng)勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。
轉(zhuǎn)載請(qǐng)注明本文地址:http://systransis.cn/yun/102809.html
摘要:無(wú)論你使用的是解釋型語(yǔ)言還是編譯型語(yǔ)言,都有一個(gè)共同的部分將源代碼作為純文本解析為抽象語(yǔ)法樹(shù)的數(shù)據(jù)結(jié)構(gòu)。和抽象語(yǔ)法樹(shù)相對(duì)的是具體語(yǔ)法樹(shù),通常稱作分析樹(shù)。這是引入字節(jié)碼緩存的原因。 這是專門探索 JavaScript 及其所構(gòu)建的組件的系列文章的第 14 篇。 想閱讀更多優(yōu)質(zhì)文章請(qǐng)猛戳GitHub博客,一年百來(lái)篇優(yōu)質(zhì)文章等著你! 如果你錯(cuò)過(guò)了前面的章節(jié),可以在這里找到它們: JavaS...
摘要:?jiǎn)?dòng)性能瓶頸分析與解決方案翻譯自的,從屬于筆者的前端入門與工程實(shí)踐。我們必須要清醒地認(rèn)識(shí)到全面評(píng)測(cè)以挖掘出真正性能瓶頸的重要性。這可能是最佳的方式了,類似于這樣的模式鼓勵(lì)基于路由的分組,目前被與廣泛使用。 JavaScript 啟動(dòng)性能瓶頸分析與解決方案 翻譯自 Addy Osmani 的 JavaScript Start-up Performance,從屬于筆者的Web 前端入門與工...
摘要:文章同步到技術(shù)內(nèi)幕之頁(yè)面渲染過(guò)程最近拜讀了傳說(shuō)中的技術(shù)內(nèi)幕一書,有很大收獲,尤其是對(duì)頁(yè)面渲染有了較深的認(rèn)識(shí)。解析語(yǔ)法分析,基于詞法解釋器生成的新標(biāo)記,構(gòu)建成抽象語(yǔ)法樹(shù),解析器嘗試將其與某條語(yǔ)法規(guī)則進(jìn)行匹配。 文章同步到github《Webkit技術(shù)內(nèi)幕》之頁(yè)面渲染過(guò)程 最近拜讀了傳說(shuō)中的《Webkit技術(shù)內(nèi)幕》一書,有很大收獲,尤其是對(duì)頁(yè)面渲染有了較深的認(rèn)識(shí)。由于功力有限,而且書中設(shè)...
摘要:文章同步到技術(shù)內(nèi)幕之頁(yè)面渲染過(guò)程最近拜讀了傳說(shuō)中的技術(shù)內(nèi)幕一書,有很大收獲,尤其是對(duì)頁(yè)面渲染有了較深的認(rèn)識(shí)。解析語(yǔ)法分析,基于詞法解釋器生成的新標(biāo)記,構(gòu)建成抽象語(yǔ)法樹(shù),解析器嘗試將其與某條語(yǔ)法規(guī)則進(jìn)行匹配。 文章同步到github《Webkit技術(shù)內(nèi)幕》之頁(yè)面渲染過(guò)程 最近拜讀了傳說(shuō)中的《Webkit技術(shù)內(nèi)幕》一書,有很大收獲,尤其是對(duì)頁(yè)面渲染有了較深的認(rèn)識(shí)。由于功力有限,而且書中設(shè)...
摘要:文章同步到技術(shù)內(nèi)幕之頁(yè)面渲染過(guò)程最近拜讀了傳說(shuō)中的技術(shù)內(nèi)幕一書,有很大收獲,尤其是對(duì)頁(yè)面渲染有了較深的認(rèn)識(shí)。解析語(yǔ)法分析,基于詞法解釋器生成的新標(biāo)記,構(gòu)建成抽象語(yǔ)法樹(shù),解析器嘗試將其與某條語(yǔ)法規(guī)則進(jìn)行匹配。 文章同步到github《Webkit技術(shù)內(nèi)幕》之頁(yè)面渲染過(guò)程 最近拜讀了傳說(shuō)中的《Webkit技術(shù)內(nèi)幕》一書,有很大收獲,尤其是對(duì)頁(yè)面渲染有了較深的認(rèn)識(shí)。由于功力有限,而且書中設(shè)...
閱讀 1698·2019-08-30 15:54
閱讀 3348·2019-08-26 17:15
閱讀 3542·2019-08-26 13:49
閱讀 2593·2019-08-26 13:38
閱讀 2307·2019-08-26 12:08
閱讀 3068·2019-08-26 10:41
閱讀 1381·2019-08-26 10:24
閱讀 3390·2019-08-23 18:35