2016-06-26 20 views
0

在學習JavaScript關閉時,我碰到了這個答案:https://stackoverflow.com/a/111111/3886155 stackoverflow。 這是關閉的一個很好的解釋。 但我在中有一些混淆例4例5Javascript關閉和全局函數的行爲

我只是複製到這裏整個片段:

例4:

var gLogNumber, gIncreaseNumber, gSetNumber; 
function setupSomeGlobals() { 
    // Local variable that ends up within closure 
    var num = 666; 
    // Store some references to functions as global variables 
    gLogNumber = function() { console.log(num); } 
    gIncreaseNumber = function() { num++; } 
    gSetNumber = function(x) { num = x; } 
} 

setupSomeGlobals(); 
gIncreaseNumber(); 
gLogNumber(); // 667 
gSetNumber(5); 
gLogNumber(); // 5 

var oldLog = gLogNumber; 

setupSomeGlobals(); 
gLogNumber(); // 666 

oldLog() // 5 

讀了一些例子後,我可以說,每當在函數內部函數執行它可以永遠記住內部外聲明的變量功能。 我同意,如果這些閉包變量無論如何更新它仍然指的是新的變量值。 我在本例中的問題與var oldLog=gLogNumber; 特別相關如何在呼叫後返回舊號碼到setupSomeGlobals();

因爲現在var num已重置。那麼爲什麼它不使用這個新的數值666?

現在實施例5:

function buildList(list) { 
    var result = []; 
    for (var i = 0; i < list.length; i++) { 
     var item = 'item' + i; 
     result.push(function() {console.log(item + ' ' + list[i])}); 
    } 
    return result; 
} 

function testList() { 
    var fnlist = buildList([1,2,3]); 
    // Using j only to help prevent confusion -- could use i. 
    for (var j = 0; j < fnlist.length; j++) { 
     fnlist[j](); 
    } 
} 

在這裏,他們有推功能集成到陣列和執行他們後循環finishes.But現在參照閉合變量是後循環finishes.Why不老一個最新的一個?

在這兩個示例中,您只是將函數定義分配給變量或數組索引。但第一個指向舊的,第二個指向latest.Why?

回答

0

如何可以調用setupSomeGlobals後返回老號()

num沒有被全局作用域,所以價值num是其中的gLogNumber引用調用內容。

再次調用setupSomeGlobals方法後,對gLogNumber的引用發生了變化。試試這個

console.log(Object.is(gLogNumber, oldLog)); //true 
setupSomeGlobals(); 
console.log(Object.is(gLogNumber, oldLog)); //false 

所以,oldLog保留舊基準和num因此舊值,但gLogNumber有了新num

但是現在引用閉包變量是 循環完成後的最後一個。爲什麼不是老的?

對於這個問題,看看

JavaScript closure inside loops – simple practical example