如何理解掌握閉包函式

2021-10-03 05:25:04 字數 2039 閱讀 3389

在理解js閉包函式之前我們應該先要了解什麼是js函式?

js函式中可以分為兩個階段:

函式定義階段

1. 在記憶體中開闢乙個儲存空間

2. 把函式體內的**當作字串一摸一樣的放在這個空間中

=> 碰到的所有變數都不進行解析

3. 把這個空間位址賦值給函式名(變數名)

=>函式呼叫階段

1. 按照函式名(變數名)找到對應的儲存空間

2. 重新開闢乙個函式執行空間

3. 在這個執行空間裡面進行形參賦值

4. 在這個執行空間裡面進行預解析

5. 把函式儲存空間的**複製乙份到執行空間裡面執行一遍

6. 執行完畢之後, 這個開闢出來的執行空間銷毀

注:在特殊情況下函式執行完畢,新開闢出來的空間也不會銷毀

如下面這段**函式的執行空間就不會銷毀

functionfn(

)var res =fn(

)

上面這段** :

res 接受的就是 函式fn 返回的那個複雜資料型別(乙個陣列)

res 接受的是 函式fn 執行空間裡面那個陣列的位址

既res 接受的是 函式fn 的執行空間內的乙個陣列

+ 只要這個陣列還存在, 就表示這個函式執行空間沒有銷毀

+ 因為一旦函式執行空間銷毀了, 那麼這個陣列也就沒有了

+ 所以這個函式執行空間不能銷毀

注:當需要銷毀這段空間的時候需要手動設定 res=null

=> 閉包的生成有三個必要條件(缺一不可)

1. 在函式 a 內部直接或者間接返回乙個函式 b

2. b 函式內部使用著 a 函式的私有變數(私有資料)

3. a 函式外部有乙個變數接受著函式 b(a函式把b函式當做返回值)

: 形成了乙個不會銷毀的函式空間

閉包空間

+ 現在我們管這個不會銷毀的 a 函式的執行空間叫做 閉包空間

+ 把函式 a 裡面返回的 函式 b, 叫做函式a 的 閉包函式

+ 官方給的定義有一句話: 閉包 => 函式內部的函式

如下面這段**: 函式作為返回值

functiona(

)}var res =a(

)

在這段**中,a()中的返回值是乙個函式b(),這個函式在a()作用域內部,所以它可以獲取a()作用域下變數num的值,將這個值作為返回值賦給全域性作用域下的變數res,實現了在全域性變數下獲取到區域性變數中的變數的值.

再來看乙個閉包的經典例子:

functionfn(

)}var res =fn(

)res()

//1 6

res(

)//1 7

一般情況下,在函式fn執行完後,就應該連同它裡面的變數一同被銷毀,但是在這個例中,函式b()作為fn的返回值被賦值給了res,這時候相當於res=b(),並且函式b()內部引用著fn裡的變數num,所以變數num無法被銷毀,而變數n是每次被呼叫時新建立的,所以每次res()執行完後它就把屬於自己的變數連同自己一起銷毀,於是乎最後就剩下孤零零的num,於是這裡就產生了記憶體消耗的問題.

綜上所訴利弊問題:

利:1、保護函式內的變數安全 ,實現封裝,防止變數流入其他環境發生命名衝突

2、在記憶體中維持乙個變數,可以做快取(但使用多了同時也是一項缺點,消耗記憶體)

3、匿名自執行函式可以減少記憶體消耗

弊:1、有一點上面已經有體現了,就是被引用的私有變數不能被銷毀,增大了記憶體消耗,造成記憶體洩漏,解決方法是可以在使用完變數後手動為它賦值為null;

2、其次由於閉包涉及跨域訪問,所以會導致效能損失,我們可以通過把跨作用域變數儲存在區域性變數中,然後直接訪問區域性變數,來減輕對執行速度的影響

如何理解閉包?

1 定義和用法 當乙個函式的返回值是另乙個函式,而返回的那個函式如果呼叫了其父函式內部的其它變數,如果返回的這個函式在外部被執行,就產生了閉包。2 表現形式 使函式外部能夠呼叫函式內部定義的變數。3 例項如下 1 根據作用域鏈的規則,底層作用域沒有宣告的變數,會向上一級找,找到就返回,沒找到就一直找...

如何理解閉包?

1 閉包是js的副產品,當你的函式訪問函式外部的變數的時候,js形成閉包,閉包實際上是作用域的逐級查詢,當b函式執行完成之後銷毀,此時a函式的被b函式引用,值並沒有被銷毀而是在記憶體中儲存了下來 function a return b var c a c 1 c 2 2 閉包應用優點 當想要提公升效...

python閉包怎麼理解 Python 閉包的理解

很多函式型的語言都有閉包這一概念,比如python的兄弟js。人們剛聽到閉包這一概念總會覺得它很晦澀,難以理解。其實不然,主要是他的名字起得太抽象了,讓人誤以為很難。下面舉乙個例子 coding utf 8 def foo nums 0 5 for i in range 5 nums i lambd...