【问题标题】:Javascript scope and hashmapsJavascript 范围和哈希图
【发布时间】:2012-01-26 04:36:20
【问题描述】:

我有一个函数可以复制包含键:函数对的映射, 用调用函数包装每个函数。

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"

【问题讨论】:

    标签: javascript scope anonymous-function


    【解决方案1】:

    您必须引入一个范围以防止 originalFunc 发生变化。函数引入了新的作用域,但 for 循环没有:

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

    【讨论】:

      【解决方案2】:

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

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

      另见javascript closure immediate evaluation

      【讨论】:

      • 在这种情况下,匿名函数是多余的,因为直接设置也可以。
      • 这不会重复功能
      【解决方案3】:

      这有 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);
      

      否则你的重复函数会丢失所有的好东西。

      【讨论】:

        【解决方案4】:

        此页面上的其他答案是正确的。但要详细解释为什么请参阅我对先前相关问题的回答:

        Please explain the use of JavaScript closures in loops

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 1970-01-01
          • 2015-02-04
          • 2012-04-15
          • 1970-01-01
          • 1970-01-01
          • 2013-03-21
          • 2021-08-03
          • 1970-01-01
          相关资源
          最近更新 更多