【问题标题】:All properties are set to last loop iteration value [why?]所有属性都设置为最后一个循环迭代值[为什么?]
【发布时间】:2013-09-15 13:39:18
【问题描述】:

示例代码:

var functions = {
 testFunction: function(){
  console.log('test');
 }      
};
var functionsClones = [];
for(i in [1,2,3]){
 var functionsClone = $.extend({}, functions);
 functionsClone.testFunction.i = i;
 functionsClones.push(functionsClone);
}

$.extend 是 jQuery 函数,它允许克隆对象而不是引用它。

现在让我们打印设置属性:

$.each(functionsClones, function(key, functionsClone){
 console.log(functionsClone.testFunction.i);
});

它输出 3 次 '2' 而不是 0、1、2。这段代码有什么问题?

【问题讨论】:

  • 不要使用for ... in 遍历数组。
  • 这个示例代码是快速编写的,只是为了演示问题:)

标签: javascript jquery arrays loops object


【解决方案1】:

因为您将i 设置在同一个testFunction 对象上(恰好是一个函数)。您不会在循环的每次迭代中创建新函数。

因此,在循环结束时,函数testFunction 对象保存它收到的最后一个值。

因为 JavaScript 只为您提供对象的引用,而不是对象本身,所以不会复制。

要制作单独的副本,您需要在循环中创建函数。

【讨论】:

  • 那么如何“克隆”函数?
  • 您需要在循环中创建函数。但是为什么你首先要在函数上放置一个属性呢?为什么不将属性直接放在functionsClone 对象上?
  • 这很复杂,我需要保持与一个库的 API 的兼容性并且必须找到一些折衷方案 :) 任何想法如何克隆函数,而不是在循环中创建它?
  • @MateuszMazurek:这很难,因为您需要考虑变量范围。它可以被克隆,但任何范围内的变量都会丢失。是否有某些原因您不只是在循环中创建一个调用您要克隆的函数的函数?
猜你喜欢
  • 1970-01-01
  • 2023-01-27
  • 1970-01-01
  • 2012-02-25
  • 2022-07-14
  • 1970-01-01
  • 2014-09-24
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多