深刻理解做用域鏈

做用域鏈是JavaScript中的一個很是重要的概念,想要理解什麼是做用域鏈,就必須知道什麼是做用域。
性能優化

做用域:函數

一、全局做用域:性能

  (1)最外層函數和在最外層函數定義的變量,擁有全局的做用域。js中一切皆對象,函數也是對象,js最外層的對象是window。因此在window下定義的函數和未被這些函數包裹的變量,就擁有全局做用域,這些變量可以在其餘任何做用域下使用。優化

  (2)全部window對象下的內置屬性屬於全局變量:如window.document,window.navigator等。spa

  (3)沒有經過var 定義,就直接賦值的變量,js會默認將其設置爲全局變量,使其擁有全局做用域。對象

二、局部做用域:事件

  (1)在函數內部或者是事件句柄中的變量和函數擁有局部做用域。局部做用域下定義的變量只能在局部使用。ip

做用域鏈作用域

     js函數也是對象,擁有能夠訪問的屬性,以及js引擎訪問的內部屬性,其中Scope屬性保存了當前函數能夠訪問的數據的集合。這個集合稱之爲做用域鏈。變量

  (1)、當函數被建立時,做用域鏈會首先填充一個全局對象,該全局對象會將全部的全局變量保存。而後做用域鏈會建立可以使用該函數的的做用域的變量的集合,如該函數的外層函數下的變量,該函數外層函數的外層函數的變量。而且最內層的集合會被推到做用域鏈的最頂端。此時全局對象會在做用域鏈的最末端。

   (2)、當函數在執行的時候,會建立一個「運行時上下文」的內部對象。這個內部對象定義了該函數執行時的環境。當「運行時上下文」被建立時,它會被初始化爲當前函數的做用域鏈全部的對象,也就是定義函數時的做用域鏈會被賦值到該運行時的做用域鏈下。而後在該函數內部定義的局部變量會被賦值到該「運行時上下文」中,組成一個新的對象:"活動對象",也就是說活動對象保存了該函數下的局部變量。並將這個活動對象推向「運行時上下文」做用域鏈的頂端。

  (3)、當函數在執行完後,「環境運行時」時被銷燬,這時的「活動對象」有兩種狀況

  一、活動對象由於無人引用而被釋放。

  二、當活動對象中被引用,沒有釋放。函數的局部變量被保存。

三、做用域鏈域性能優化

  當函數在被執行的時候,每遇到一個變量都會從活動對象開始遍歷解析,若是找到就使用該變量,若是沒有找到就接着下一個變量找,在做用域鏈中都沒有找到的話,這個值就是未定義的。

  因此咱們知道了這個過程,在編寫代碼的時候儘可能少定義全局變量,由於在一個局部做用域中使用全局變量的時候,老是會在最後查找全局變量,當函數嵌套很深的時候,遍歷的過程就越長,對性能有必定影響。因此最好定義局部變量,並且出來性能以外,定義局部變量還有其餘好處,如避免全局污染等。

注:本隨筆的內容依據夢想天空(jzhula.com)而來,加入了本身的理解。若有不到位或者錯誤之處,煩請指出!

相關文章
相關標籤/搜索