JavaScript的作用域問題

JavaScript作用域應該是JavaScript裏面最難理解的概念了。看了《JavaScript高級程序設計》和其他的書雖然費了很大力氣看懂了,感覺解釋的還是有點費解。正好在網上看到幾個面試題可以用作用域解決,也方便了對它的理解。

1.JavaScript是單線程程序

和其他語言當初設計的時候不一樣,JavaScript是單線程(一個時機段內只幹一件事情),是不支持併發這個概念的。爲什麼會這樣呢?可以這樣理解,假如一個線程正在創建DOM對象,然後下面一個線程將DOM對象刪除了,這樣矛盾嗎?另外一個問題就是現在很火的Node也是單線程。非常重要的是JavaScript的單線程對頁面解析而言,從上到下。傻瓜式的執行。

2.JavaScript預解析機制

先來看一個程序的執行結果:

alert(a);//function a(){alert(4);}
var a = 1 ;
alert(a);//1
function a(){alert(2);}
alert(a);//1
var a = 3 ;
alert(a);//3
function a(){alert(4);}
alert(a);//3

JavaScript解析器在解析的代碼的時候可以簡單的分爲兩個步驟(結合上述代碼):
第一步:遍歷代碼尋找var變量、function函數、參數
a.將所有的var變量設置爲undefined

  • a = undefined

b.將所有的函數體賦值給函數指針

  • a = function a(){alert(2);}
  • a = function a(){alert(4);}

c.整合上述兩個步驟,其中+-*/%等具有運算功能進行賦值,後面的會覆蓋前面的,所以上面的a、b兩個步驟執行完過後就剩下:

  • a = function a(){alert(4);}

第二步:逐行掃描代碼
在逐行掃描的過程中,會隨時查看第一步中計算的結果a = function a(){alert(4);} 同時我們知道運算符具有賦值功能,會修改變量的值,而函數不具有賦值的功能。執行第一行代碼alert(a)發現第一步執行結果是a = function a(){alert(4);}所以alert(a)的結果是 function a(){alert(4);}掃描第二行var a = 1; 發現有=具有賦值功能可以修改變量的值從而將a變量修改爲var a = 1;掃描第三行發現現在有var a = 1;所以alert(a)結果是1,掃描第四行代碼function a(){alert(2);}發現是函數所以沒有賦值的功能。無法修改變量的值。所以第五行代碼alert(a)的執行結果是1。掃描第六行代碼var a = 3 ;所以變量a被修改爲var a = 3 ;第七行代碼執行結果是3;掃描第八行代碼發現是函數function a(){alert(4);}無法修改變量的值,所以下面alert(a)執行的結果是3,上面整個流程就分析完了。

(這裏不探討所謂的語法、詞法這些編譯原理方面的知識)

3.JavaScript作用域鏈的簡單理解

先看下面這個筆試題目:

var str = 'jQuery';
function fun(){
     alert(str);//jQuery
     str = 'JavaScript';
 }
 fun();
 alert(str);//JavaScript

按照上面將的兩步方法進行分析,第一步:先找var變量、function函數、參數

var str = undefined
fun = fun(){………..}

第二步:逐行掃描代碼第一行將變量str修改爲var str = 'jQuery';第二行行數沒有賦值功能,第六行是函數調用,只要發生函數調用,繼續第一步尋找變量、函數和參數,發現沒有var變量函數和參數,這個時候將向函數外層尋找變量,這就是作用域鏈的概念,裏面沒有繼續向外層尋找變量。發現有變量var str = 'jQuery';所以結果是jQuery,向下執行代碼str = 'JavaScript'操作符號可以進行賦值,發現外部有str同名變量所以有var str = 'JavaScript',所以最後一行執行結果是JavaScript

以上就是今天的內容,內容不多但是不是很好理解。建議多分析多思考。和實際案例結合。。。實踐出真知!


相關文章



非常高興和大家交流學習
自由轉載,創意許可,請文章來源,來自這裏
(http://blog.csdn.net/unikylin)

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章