Javascript范围和哈希映射

时间:2011-12-22 14:48:54

标签: javascript scope anonymous-function

我有一个复制包含key:function对的地图的函数, 用调用函数包装每个函数。

function duplicateFunctionsMap(functionsMap){

    var newMap = {};

    for (var name in functionsMap){

        var originalFunc = functionsMap[name];

        newMap[name] = function(){
            originalFunc();
        }
    }

    return  newMap;
}

现在尝试运行重复映射中的任何条目总是调用最后一个

duplicateFunctionsMap({
                      first: function(){alert("first");}, 
                       last: function(){alert("last");}
                      })["first"](); // outputs "last"

4 个答案:

答案 0 :(得分:3)

您必须引入范围以防止originalFunc发生变化。函数引入了新范围,但for循环不会:

for (var name in functionsMap){
    (function(originalFunc) {
        newMap[name] = function(){
            originalFunc();
        }; // <-- add semicolon at end of expression, too
    })(functionsMap[name]);
}

答案 1 :(得分:2)

这有900万重复,但在这里它... javascript 没有块级范围。重复一遍。

所以它变成了:

function duplicateFunctionsMap(functionsMap) {

    var newMap = {};

    for (var name in functionsMap) {
         var originalFunc = functionsMap[name];

        newMap[name] = (function (originalFunc) {
            return function () {
            originalFunc();
            };
        })(originalFunc);

    }

    return newMap;
}

请注意,如果要复制使用上下文,参数和返回值的函数,则需要执行此操作:

newMap[name] = (function (originalFunc) {
    return function () {
        return originalFunc.apply(this, arguments);
    };
})(originalFunc);

否则你的重复功能会丢失所有好东西。

答案 2 :(得分:0)

在你的for循环中,你可能已经创建了一个闭包。尝试这个代码创建一个内部匿名立即执行的函数

for (var name in functionsMap){
    (function(_of) { 
        newMap[name] =  _of;
    }(functionsMap[name]))
}

另见javascript closure immediate evaluation

答案 3 :(得分:0)

此页面上的其他答案都是正确的。但是为了详细解释为什么看到我之前相关问题的答案:

Please explain the use of JavaScript closures in loops