首頁  >  文章  >  web前端  >  關於JavaScript閉包的小結

關於JavaScript閉包的小結

一个新手
一个新手原創
2017-09-06 13:44:141824瀏覽

 這次是一篇讀後感

深入理解javasrcipt原型與閉包-閉包

Javasrcipt秘密花園-函數之閉包與引用

#通讀兩篇關於閉包的文章之後,還是有點收穫的,就總結一下,怕自己忘記

#好,下面開始我的表演

閉包是什麼?

閉包是 JavaScript 一個非常重要的特性,這表示目前作用域總是能夠存取外部作用域中的變數。

(而在通常情況下目前作用域只能存取本身或上級的作用域),作用域這一部分下次再寫

函數是JavaScript 中唯一擁有自身作用域的結構,所以閉包的創建依賴函數。

閉包的時候,函數有兩種情況,

一種是函數作為傳回值

一種是函數作為參數傳遞

1。函數作為傳回值


function nihao(){var i=0;return  function get(i){
    i++;    return i;
}
}var f=nihao();
f(1);

我們在控制台執行之後結果如下

執行結果為2

我們把get函數當作回傳值賦值給變數f,執行f(1)的時候,直接進入到get的作用域下,1賦值給i,執行完i++,i變成2,之後return i

 2。函數作為參數傳遞


var a=2,b=function(c){      
    if(c>a){
      console.log(c);  
}     
};
(function(f1){    
    var a=5;
    f1(3)
})(b);

我們在控制台列印一下

##結果為3,

可以看到,我們執行了一個匿名包裝器(自執行匿名函數),然後把函數b當作參數傳到了匿名函數裡面。

執行f1(3)其實就是在執行b=function(3)

這裡有一個問題,我們在匿名包裝器內執行的時候,a已經重新定義為5,但是在執行到f1的時候,a又變為了2,所以3>2成立,執行了console.log

根據執行結果,我是這麼理解的,當調用f1函數的時候,其實就是進入b=function()的作用域下了,而b又是用函數賦值表達式定義的函數

所以,函數b和a其實是在同一個作用域下的,這個時候也會執行var a=2;等於是重新定義了一下a,所以當執行if(c>a)的時候,a就已經重新定義為2 

以為已經結束了?

錯,我又去用函數宣告的方式測試了一下結果

是的,就算透過函數宣告的方式定義的b也是一樣結果為3

所以這個和函數的定義方式無關,無論是函數宣告還是函數賦值表達式來定義,結果都是一樣的

#那麼只能這麼理解了

當我們執行f1(3)的時候,作用域就已經改變了,從匿名包裝器中的作用域轉移到了function b() 或者說var  b=function()所在的作用域中了

接著會執行if判斷,會尋找a,在函數b中沒找到,然後向父級中尋找,這裡定義了一個var a=2;這個時候a就找到了,然後繼續執行if語句

3>2,接著執行console.log,輸出3

總結了,兩個又好像沒有總結,完了,

算了,先寫下一個把

好,我們看在秘密花園中是這麼寫的


function Counter(start) {    
        var count = start;    
        return {
        increment: function() {
            count++;
        },

        get: function() {            
        return count;
        }
    }
}var foo = Counter(4);
foo.increment();
foo.get();

看一下執行結果

我們來分析一下,這個什麼鬼的執行順序,

首先透過函數賦值表達式的方式把Counter方法賦值給變數foo,那麼foo現在也是一個函數了

因為JavaScript 中不可以對作用域進行引用或賦值,因此沒有辦法在外部存取 count 變數。 唯一的途徑就是透過閉包。

賦值的時候還傳了一個參數4,那麼我們執行foo.increment()的時候,這個時候已經就是閉包了,

所以count就為4,然後執行了count++;

接著執行foo.get();進入了第二個閉包,會回傳count,因為count++了所以這個時候count就為5,return count,回傳的就是5;

以上是關於JavaScript閉包的小結的詳細內容。更多資訊請關注PHP中文網其他相關文章!

陳述:
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn