1. 程式人生 > >js對程式碼解析機制

js對程式碼解析機制

JavaScript執行三部曲
指令碼執行js引擎都做了什麼呢? 1.語法分析 2.預編譯 3.解釋執行 在執行程式碼前,還有兩個步驟 語法分析很簡單,就是引擎檢查你的程式碼有沒有什麼低階的語法錯誤 解釋執行顧名思義便是執行程式碼了 預編譯簡單理解就是在記憶體中開闢一些空間,存放一些變數與函式 理解了預編譯對大家理解作用域同樣有幫助 JS預編譯什麼時候發生 我當初思維誤區也發生在這裡 預編譯到底什麼時候發生 希望大家不要讓上面的執行過程讓你產生誤會, 誤以為預編譯僅僅發生在script內程式碼塊執行前 這倒並沒有錯 預編譯確確實實在script程式碼內執行前發生了 但是它大部分會發生在函式執行前 JS預編譯例項 舉例前,先來思考一下這幾個概念: 變數宣告
var… 函式宣告 function<script> var a = 1;// 變數宣告 function b(y){//函式宣告 var x = 1; console.log('so easy'); }; var c = function(){//是變數宣告而不是函式宣告,這種寫法是變數賦值,函式在js語言裡也是一種資料,匿名函式作為變數賦值給定義的變數。這種形式在預編譯處理階段,只會給變數a分配一個記憶體空間,不會做初始化。初始化過程中會在執行時執行。 //... } b(100); </script> <script> var
d = 0; </script> 讓我們看看引擎對這段程式碼做了什麼吧 頁面產生便建立了GO全域性物件(Global Object)(也就是大家熟悉的window物件) 第一個指令碼檔案載入 指令碼載入完畢後,分析語法是否合法 開始預編譯 查詢變數宣告,作為GO屬性,值賦予undefined 查詢函式宣告,作為GO屬性,值賦予函式體 //虛擬碼 GO/window = { //頁面載入建立GO同時,建立了document、navigator、screen等等屬性,此處省略 a: undefined, c: undefined, b: function(y){
var x = 1; console.log('so easy'); } } 解釋執行程式碼(直到執行函式b) //虛擬碼 GO/window = { //變數隨著執行流得到初始化 a: 1, c: function(){ //... }, b: function(y){ var x = 1; console.log('so easy'); } } 執行函式b之前,發生預編譯 建立AO活動物件(Active Object) 查詢形參和變數宣告,值賦予undefined 實參值賦給形參 查詢函式宣告,值賦予函式體 //虛擬碼 AO = { //建立AO同時,建立了arguments等等屬性,此處省略 y: 100, x: undefined } 解釋執行函式中程式碼 第一個指令碼檔案執行完畢,載入第二個指令碼檔案 第二個指令碼檔案載入完畢後,進行語法分析 語法分析完畢,開始預編譯 重複最開始的預編譯步驟…… 大家要注意, 預編譯階段發生變數宣告和函式宣告,沒有初始化行為(賦值),匿名函式不參與預編譯 只有在解釋執行階段才會進行變數初始化 嗯~最後收一下尾 總結 預編譯(函式執行前)※ 1. 建立AO物件(Active Object) 2. 查詢函式形參及函式內變數宣告,形參名及變數名作為AO物件的屬性,值為undefined 3. 實參形參相統一,實參值賦給形參 4. 查詢函式宣告,函式名作為AO物件的屬性,值為函式引用 預編譯(指令碼程式碼塊script執行前) 1. 查詢全域性變數宣告(包括隱式全域性變數宣告,省略var宣告),變數名作全域性物件的屬性,值為undefined 3. 查詢函式宣告,函式名作為全域性物件的屬性,值為函式引用