在迭代期间向JSON对象添加属性?

时间:2016-06-29 19:47:30

标签: javascript json object iteration

Mozilla开发中心说:

  

最好不要添加,修改或删除对象的属性   在迭代期间,除了当前正在访问的属性;   无法保证是否会访问附加财产,

但是,我没有必要再访问添加的属性。那么添加它们是否安全?

E.g。

var animals = {"cats":25, "dogs":15}
for(var key in animals){
    if(key.substring(0,3) !=="big"){ // no danger of referencing them
        var newAnimal = "big" + key;
        animals[newAnimal] =0;
    }
} 

或者增加对象的大小会混淆" for - in"迭代?

4 个答案:

答案 0 :(得分:3)

文档并没有说添加的项目不会被访问,他们说它未定义。

因此,根据实施情况,您最终可能会遇到 bigdogs bigbigdogs 等,导致无限循环。 或者它可能会做一些完全不同的事情,毕竟,它是未定义的行为。

要解决此问题,请使用对象的副本,并将新属性添加到副本,而不会改变循环对象。

编辑:看起来您正在检查密钥是否以 big 开头,当我第一次看到它时错过了。所以你应该没事。

避免像这样的未定义行为仍然是一种好习惯。当代码必须在将来某个时候被更改并且循环/检查背后的推理并不是绝对清楚的时候,这很容易回来并咬你。

答案 1 :(得分:1)

如果您不关心"无法保证是否会访问添加的属性",那么您可以这样做。

如果您想确保无法访问它们,请在循环之前制作属性的快照:



var animals = {"cats":25, "dogs":15}
for(var key of Object.keys(animals))
  animals["big" + key] = 0;
console.log(animals);




如果您想确保访问它们,请使用地图:



var animals = new Map([ ["cats",25], ["dogs",15]]);
for(var key of animals.keys())
  if(key.slice(0,6) !== 'bigbig')
    animals.set("big" + key, 0);
console.log([...animals].map(a => a.join(': ')));




答案 2 :(得分:0)

是的,添加它们是安全的,因为您已经检查以确保不会以无限循环结束。

"添加"在随机的地方添加它,所以顺序不是你可以依赖的东西,但是看起来你不需要在同一个循环中访问新创建的属性,这应该没问题。

我建议如果您只是想添加新属性,请创建一个新对象,稍后在完成后将替换当前对象。因为这样会有更好的表现。

也不会驱动正在审核您的代码的人:)。祝你有个美好的一天

答案 3 :(得分:0)

安全

开始迭代后,

  • 在访问之前删除一个项目,你没有看到它。
  • 更新项目,您会看到新值
  • 插入一个项目,您可能会或可能不会在当前的cicle中看到它。但这也很安全。

https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Statements/for...in