js之lhs/rhs

傳統(tǒng)編譯語言的流程中痢虹,程序中的一段源代碼在執(zhí)行之前會經(jīng)歷三個步驟,統(tǒng)稱為“編譯”。
分詞/詞法分析(Tokenizing/Lexing)
這個過程會將由字符組成的字符串分解成(對編程語言來說)有意義的代碼塊,這些代碼塊被稱為詞法單元(token)。例如蓝纲,考慮程序var a = 2;
。這段程序通常會被分解成為下面這些詞法單元:var晌纫、a税迷、=、2
锹漱、;箭养。空格是否會被當作詞法單元哥牍,取決于空格在這門語言中是否具有意義毕泌。
分詞(tokenizing)和詞法分析(Lexing)之間的區(qū)別是非常微妙、晦澀的嗅辣,主要差異在于詞法單元的識別是通過有狀態(tài)還是無狀態(tài)的方式進行的撼泛。簡單來說,如果詞法單元生成器在判斷a
是一個獨立的詞法單元還是其他詞法單元的一部分時澡谭,調(diào)用的是有狀態(tài)的解析規(guī)則愿题,那么這個過程就被稱為詞法分析

解析/語法分析(Parsing)
這個過程是將詞法單元流(數(shù)組)轉(zhuǎn)換成一個由元素逐級嵌套所組成的代表了程序語法結(jié)構(gòu)的樹。這個樹被稱為“抽象語法樹”(Abstract Syntax Tree潘酗,AST)杆兵。var a = 2;的抽象語法樹中可能會有一個叫作VariableDeclaration的頂級節(jié)點,接下來是一個叫作Identifier(它的值是a)的子節(jié)點仔夺,以及一個叫作AssignmentExpression的子節(jié)點琐脏。AssignmentExpression節(jié)點有一個叫作NumericLiteral(它的值是2)的子節(jié)點。

代碼生成
將AST轉(zhuǎn)換為可執(zhí)行代碼的過程被稱為代碼生成缸兔。這個過程與語言日裙、目標平臺等息息相關(guān)。拋開具體細節(jié)灶体,簡單來說就是有某種方法可以將var a = 2;的AST轉(zhuǎn)化為一組機器指令阅签,用來創(chuàng)建一個叫作a的變量(包括分配內(nèi)存等)掐暮,并將一個值儲存在a中蝎抽。

關(guān)于引擎如何管理系統(tǒng)資源超出了我們的討論范圍,因此只需要簡單地了解引擎可以根據(jù)需要創(chuàng)建并儲存變量即可路克。

比起那些編譯過程只有三個步驟的語言的編譯器樟结,JavaScript引擎要復雜得多。例如精算,在語法分析和代碼生成階段有特定的步驟來對運行性能進行優(yōu)化瓢宦,包括對冗余元素進行優(yōu)化等。
因此在這里只進行宏觀灰羽、簡單的介紹驮履,接下來你就會發(fā)現(xiàn)我們介紹的這些看起來有點高深的內(nèi)容與所要討論的事情有什么關(guān)聯(lián)。
首先廉嚼,JavaScript引擎不會有大量的(像其他語言編譯器那么多的)時間用來進行優(yōu)化玫镐,因為與其他語言不同,JavaScript的編譯過程不是發(fā)生在構(gòu)建之前的怠噪。
對于JavaScript來說恐似,大部分情況下編譯發(fā)生在代碼執(zhí)行前的幾微秒(甚至更短!)的時間內(nèi)傍念。在我們所要討論的作用域背后矫夷,JavaScript引擎用盡了各種辦法(比如JIT,可以延遲編譯甚至實施重編譯)來保證性能最佳憋槐。
簡單地說双藕,任何JavaScript代碼片段在執(zhí)行前都要進行編譯(通常就在執(zhí)行前)。因此阳仔,JavaScript編譯器首先會對var a = 2;
這段程序進行編譯忧陪,然后做好執(zhí)行它的準備,并且通常馬上就會執(zhí)行它。
總之:js執(zhí)行是先通過編譯器編譯好赤嚼,然后js引擎對其執(zhí)行
例如:處理var a = 2;
引擎
從頭到尾負責整個JavaScript程序的編譯及執(zhí)行過程旷赖。
編譯器
引擎的好朋友之一,負責語法分析及代碼生成等臟活累活(詳見前一節(jié)的內(nèi)容)更卒。
作用域
引擎的另一位好朋友等孵,負責收集并維護由所有聲明的標識符(變量)組成的一系列查詢,并實施一套非常嚴格的規(guī)則蹂空,確定當前執(zhí)行的代碼對這些標識符的訪問權(quán)限俯萌。

當你看見var a = 2;這段程序時,很可能認為這是一句聲明上枕。但我們的新朋友引擎卻不這么看咐熙。事實上,引擎認為這里有兩個完全不同的聲明辨萍,一個由編譯器在編譯時處理棋恼,另一個則由引擎在運行時處理。
下面我們將var a = 2;分解锈玉,看看引擎和它的朋友們是如何協(xié)同工作的爪飘。
編譯器首先會將這段程序分解成詞法單元,然后將詞法單元解析成一個樹結(jié)構(gòu)拉背。但是當編譯器開始進行代碼生成時师崎,它對這段程序的處理方式會和預期的有所不同。
可以合理地假設(shè)編譯器所產(chǎn)生的代碼能夠用下面的偽代碼進行概括:“為一個變量分配內(nèi)存椅棺,將其命名為a犁罩,然后將值2保存進這個變量×骄危”然而床估,這并不完全正確。
事實上編譯器會進行如下處理鬼雀。

  1. 遇到var a顷窒,編譯器會詢問作用域是否已經(jīng)有一個該名稱的變量存在于同一個作用域的集合中。如果是源哩,編譯器會忽略該聲明鞋吉,繼續(xù)進行編譯;否則它會要求作用域在當前作用域的集合中聲明一個新的變量励烦,并命名為a谓着。

  2. 接下來編譯器會為引擎生成運行時所需的代碼,這些代碼被用來處理a = 2這個賦值操作坛掠。引擎運行時會首先詢問作用域赊锚,在當前的作用域集合中是否存在一個叫作a的變量治筒。如果是,引擎就會使用這個變量舷蒲;如果不是耸袜,引擎會繼續(xù)查找該變量(查看1.3節(jié))。

如果引擎最終找到了a變量牲平,就會將2賦值給它堤框。否則引擎就會舉手示意并拋出一個異常!

總結(jié):變量的賦值操作會執(zhí)行兩個動作纵柿,首先編譯器會在當前作用域中聲明一個變量(如果之前沒有聲明過)蜈抓,然后在運行時引擎會在作用域中查找該變量,如果能夠找到就會對它賦值昂儒。

編譯器:
編譯器在編譯過程的第二步中生成了代碼沟使,引擎執(zhí)行它時,會通過查找變量a來判斷它是否已聲明過渊跋。查找的過程由作用域進行協(xié)助腊嗡,但是引擎執(zhí)行怎樣的查找,會影響最終的查找結(jié)果刹枉。引擎有兩種查找方式LHS/RHS(左右查找)

在我們的例子中叽唱,引擎會為變量a進行LHS查詢。另外一個查找的類型叫作RHS微宝。
LHS:左查找,就是在從等號的左邊進行查找虎眨,意思就是說我們要給查詢到的變量賦值蟋软,首先得查詢是否申明了這個變量,然后才能賦值的吧嗽桩!這時候用到的查詢就是從左邊查詢(LHS)(賦值操作)岳守,理解為賦值操作的目標。
LHS查詢比較松散碌冶,如果查詢不到湿痢,就會創(chuàng)建一個全局的,不會拋出異常
RHS:右查詢就是我們要獲得這個變量的值扑庞,查找變量是否存在譬重,然后獲取到值。理解為賦值操作的源頭罐氨。
左邊需要被賦值的是LHS查找臀规,右邊需要找到他的值然后進行操作的是RHS查找。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末栅隐,一起剝皮案震驚了整個濱河市塔嬉,隨后出現(xiàn)的幾起案子玩徊,更是在濱河造成了極大的恐慌,老刑警劉巖谨究,帶你破解...
    沈念sama閱讀 217,406評論 6 503
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件恩袱,死亡現(xiàn)場離奇詭異,居然都是意外死亡胶哲,警方通過查閱死者的電腦和手機憎蛤,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,732評論 3 393
  • 文/潘曉璐 我一進店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來纪吮,“玉大人俩檬,你說我怎么就攤上這事∧朊耍” “怎么了棚辽?”我有些...
    開封第一講書人閱讀 163,711評論 0 353
  • 文/不壞的土叔 我叫張陵,是天一觀的道長冰肴。 經(jīng)常有香客問我屈藐,道長,這世上最難降的妖魔是什么熙尉? 我笑而不...
    開封第一講書人閱讀 58,380評論 1 293
  • 正文 為了忘掉前任联逻,我火速辦了婚禮,結(jié)果婚禮上检痰,老公的妹妹穿的比我還像新娘包归。我一直安慰自己,他們只是感情好铅歼,可當我...
    茶點故事閱讀 67,432評論 6 392
  • 文/花漫 我一把揭開白布公壤。 她就那樣靜靜地躺著,像睡著了一般椎椰。 火紅的嫁衣襯著肌膚如雪厦幅。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 51,301評論 1 301
  • 那天慨飘,我揣著相機與錄音确憨,去河邊找鬼。 笑死瓤的,一個胖子當著我的面吹牛休弃,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播堤瘤,決...
    沈念sama閱讀 40,145評論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼玫芦,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了本辐?” 一聲冷哼從身側(cè)響起桥帆,我...
    開封第一講書人閱讀 39,008評論 0 276
  • 序言:老撾萬榮一對情侶失蹤医增,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后老虫,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體叶骨,經(jīng)...
    沈念sama閱讀 45,443評論 1 314
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 37,649評論 3 334
  • 正文 我和宋清朗相戀三年祈匙,在試婚紗的時候發(fā)現(xiàn)自己被綠了忽刽。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點故事閱讀 39,795評論 1 347
  • 序言:一個原本活蹦亂跳的男人離奇死亡夺欲,死狀恐怖跪帝,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情些阅,我是刑警寧澤伞剑,帶...
    沈念sama閱讀 35,501評論 5 345
  • 正文 年R本政府宣布,位于F島的核電站市埋,受9級特大地震影響黎泣,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜缤谎,卻給世界環(huán)境...
    茶點故事閱讀 41,119評論 3 328
  • 文/蒙蒙 一抒倚、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧坷澡,春花似錦托呕、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,731評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至姻政,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間岂嗓,已是汗流浹背汁展。 一陣腳步聲響...
    開封第一講書人閱讀 32,865評論 1 269
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留厌殉,地道東北人食绿。 一個月前我還...
    沈念sama閱讀 47,899評論 2 370
  • 正文 我出身青樓,卻偏偏與公主長得像公罕,于是被迫代替她去往敵國和親器紧。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當晚...
    茶點故事閱讀 44,724評論 2 354

推薦閱讀更多精彩內(nèi)容