我有一个像以下JavaScript对象:
var p = {
"p1": "value1",
"p2": "value2",
"p3": "value3"
};
现在我想循环遍历所有 p
元素(p1
,p2
,p3
......)并获得他们的钥匙和价值观。我怎样才能做到这一点?
如有必要,我可以修改JavaScript对象。我的最终目标是遍历一些键值对,如果可能的话,我想避免使用 eval
。
我有一个像以下JavaScript对象:
var p = {
"p1": "value1",
"p2": "value2",
"p3": "value3"
};
现在我想循环遍历所有 p
元素(p1
,p2
,p3
......)并获得他们的钥匙和价值观。我怎样才能做到这一点?
如有必要,我可以修改JavaScript对象。我的最终目标是遍历一些键值对,如果可能的话,我想避免使用 eval
。
你可以使用 for-in
循环如其他人所示。但是,您还必须确保获得的密钥是对象的实际属性,而不是来自原型。
这是片段:
var p = {
"p1": "value1",
"p2": "value2",
"p3": "value3"
};
for (var key in p) {
if (p.hasOwnProperty(key)) {
console.log(key + " -> " + p[key]);
}
}
在ECMAScript 5下,您可以组合使用 Object.keys()
和 Array.prototype.forEach()
:
var obj = { first: "John", last: "Doe" };
Object.keys(obj).forEach(function(key) {
console.log(key, obj[key]);
});
ES6补充道 for...of
:
for (const key of Object.keys(obj)) {
console.log(key, obj[key]);
}
ES2017补充道 Object.entries()
这避免了必须查找原始对象中的每个值:
Object.entries(obj).forEach(
([key, value]) => console.log(key, value)
);
都 Object.keys()
和 Object.entries()
以与a相同的顺序迭代属性 for...in
循环 但忽略原型链。只迭代对象自己的可枚举属性。
编辑:ES2016→ES6
你必须使用 for-in循环
但是在使用这种循环时要非常小心,因为这样会 循环原型链中的所有属性。
因此,在使用for-in循环时,请始终使用 hasOwnProperty
确定迭代中的当前属性是否确实是您正在检查的对象的属性的方法:
for (var prop in p) {
if (!p.hasOwnProperty(prop)) {
//The current property is not a direct property of p
continue;
}
//Do your logic with the property here
}
如果我们不提及循环对象的替代方法,那么问题就不会完整。
如今,许多众所周知的JavaScript库提供了自己的迭代集合的方法,即over 阵列, 对象,和 类似数组的对象。这些方法使用方便,并且与任何浏览器完全兼容。
如果你合作 jQuery的,你可以使用 jQuery.each()
方法。它可用于无缝迭代对象和数组:
$.each(obj, function(key, value) {
console.log(key, value);
});
在 Underscore.js 你可以找到方法 _.each()
,迭代一个元素列表,依次产生一个提供的函数(注意参数的顺序) iteratee 功能!):
_.each(obj, function(value, key) {
console.log(key, value);
});
罗短跑 提供了几种迭代对象属性的方法。基本 _.forEach()
(或者它的别名 _.each()
)用于循环遍历对象和数组,但是(!)对象 length
属性被视为数组,为避免这种行为,建议使用 _.forIn()
和 _.forOwn()
方法(这些也有 value
争论第一):
_.forIn(obj, function(value, key) {
console.log(key, value);
});
_.forIn()
迭代 拥有和继承 对象的可枚举属性,而 _.forOwn()
只迭过 拥有 对象的属性(基本上是检查 hasOwnProperty
功能)。对于简单对象和对象文字,这些方法中的任何一种都可以正常工作。
通常,所有描述的方法与任何提供的对象具有相同的行为。除了使用原生 for..in
循环通常是 更快 比任何抽象,如 jQuery.each()
,这些方法相当容易使用,需要较少的编码并提供更好的错误处理。
在ECMAScript 5中,您在文字的迭代字段中有了新的方法 - Object.keys
您可以看到更多信息 MDN
我的选择如下是当前版本浏览器中的更快解决方案(Chrome30,IE10,FF25)
var keys = Object.keys(p),
len = keys.length,
i = 0,
prop,
value;
while (i < len) {
prop = keys[i];
value = p[prop];
i += 1;
}
您可以将此方法的性能与不同的实现进行比较 jsperf.com:
您可以看到浏览器支持 Kangax的compat表
UPD:
此问题中所有最常见案例的性能比较 perfjs.info
:
您可以像以下一样迭代它:
for (var key in p) {
alert(p[key]);
}
注意 key
不会承担财产的价值,它只是一个指数值。
由于es2015越来越受欢迎,我发布这个答案,包括使用生成器和迭代器来顺利迭代 [key, value]
对。因为在其他语言中可以使用例如Ruby。
好的,这是一个代码:
const MyObject = {
'a': 'Hello',
'b': 'it\'s',
'c': 'me',
'd': 'you',
'e': 'looking',
'f': 'for',
[Symbol.iterator]: function* () {
for (const i of Object.keys(this)) {
yield [i, this[i]];
}
}
};
for (const [k, v] of MyObject) {
console.log(`Here is key ${k} and here is value ${v}`);
}
有关如何在开发人员Mozilla页面上找到迭代器和生成器的所有信息。
希望它帮助了某人。
编辑:
ES2017将包括 Object.entries
这会迭代 [key, value]
对象中的对更加容易。现在已经知道它将成为标准的一部分 ts39 舞台信息。
我认为是时候更新我的答案,让它变得比现在更新鲜。
const MyObject = {
'a': 'Hello',
'b': 'it\'s',
'c': 'me',
'd': 'you',
'e': 'looking',
'f': 'for',
};
for (const [k, v] of Object.entries(MyObject)) {
console.log(`Here is key ${k} and here is value ${v}`);
}
您可以找到有关使用的更多信息 MDN 页