繁体   English   中英

JavaScript闭包和全局函数的行为

[英]Behaviors of Javascript closures and global functions

在学习javascript闭包时,我在stackoverflow上遇到了这个答案https://stackoverflow.com/a/111111/3886155 这是对闭包的很好解释。 但是我对示例4示例5感到有些困惑。

我只是在这里复制整个代码段:

范例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;特别相关var oldLog=gLogNumber; 调用setupSomeGlobals();后如何返回旧数字setupSomeGlobals();

因为现在var num已重置。所以为什么不使用这个新的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]();
    }
}

这里他们将函数推入数组并在循环完成后执行它们,但是现在引用闭包变量是循环完成后的最新一个,为什么不是旧的呢?

在两个示例中,您都只是将函数定义分配给变量或数组索引,但是第一个指向旧的而第二个指向最新的。

调用setupSomeGlobals()后如何返回旧数字

num不在全局范围内,因此num值在调用gLogNumber的引用的上下文中。

再次调用setupSomeGlobals方法后,对gLogNumber引用gLogNumber更改。 尝试这个

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

因此, oldLog保留了旧的引用,因此保留了num旧值,但是gLogNumber获得了新的num

但是现在对闭包变量的引用是循环结束后最新的一个,为什么不是旧的呢?

对于这个问题,看看

循环内的JavaScript封闭-简单的实际示例

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM