我有一个包含对象和数组的嵌套数据结构。我如何提取信息,即访问一个特定的或多个值(或键)?
例如:
var data = {
code: 42,
items: [{
id: 1,
name: 'foo'
}, {
id: 2,
name: 'bar'
}]
};
我如何访问项目中的第二个项目的名称?
我有一个包含对象和数组的嵌套数据结构。我如何提取信息,即访问一个特定的或多个值(或键)?
例如:
var data = {
code: 42,
items: [{
id: 1,
name: 'foo'
}, {
id: 2,
name: 'bar'
}]
};
我如何访问项目中的第二个项目的名称?
当前回答
这个问题很老了,所以作为当代的更新。随着ES2015的开始,有了其他方法来获取你需要的数据。现在有一个被称为对象解构的特性,用于访问嵌套对象。
Const data = { 42岁的代码: 项目:[{ id: 1、 名称:“foo” }, { id: 2 名称:“酒吧” }) }; const { 项目:[,{ 名称:secondName }) } =数据; console.log (secondName);
上面的例子从名为items的数组的name键创建了一个名为secondName的变量,该数组表示跳过数组中的第一个对象。
值得注意的是,对于这个例子来说,它可能有点过头了,因为简单的数组访问更容易阅读,但在一般情况下,它在分解对象时很有用。
这是对您的特定用例的非常简短的介绍,解构可能是一种不寻常的语法,首先要习惯。我建议阅读Mozilla的解构赋值文档来了解更多信息。
其他回答
动态访问多级对象。
var obj = {
name: "john doe",
subobj: {
subsubobj: {
names: "I am sub sub obj"
}
}
};
var level = "subobj.subsubobj.names";
level = level.split(".");
var currentObjState = obj;
for (var i = 0; i < level.length; i++) {
currentObjState = currentObjState[level[i]];
}
console.log(currentObjState);
工作提琴:https://jsfiddle.net/andreitodorut/3mws3kjL/
我就是这么做的。
let groups = [
{
id:1,
title:"Group 1",
members:[
{
id:1,
name:"Aftab",
battry:'10%'
},
{
id:2,
name:"Jamal",
},
{
id:3,
name:"Hamid",
},
{
id:4,
name:"Aqeel",
},
]
},
{
id:2,
title:"Group 2",
members:[
{
id:1,
name:"Aftab",
battry:'10%'
},
{
id:2,
name:"Jamal",
battry:'10%'
},
{
id:3,
name:"Hamid",
},
]
},
{
id:3,
title:"Group 3",
members:[
{
id:1,
name:"Aftab",
battry:'10%'
},
{
id:3,
name:"Hamid",
},
{
id:4,
name:"Aqeel",
},
]
}
]
groups.map((item) => {
// if(item.id == 2){
item.members.map((element) => {
if(element.id == 1){
element.battry="20%"
}
})
//}
})
groups.forEach((item) => {
item.members.forEach((item) => {
console.log(item)
})
})
// const path = 'info.value[0].item'
// const obj = { info: { value: [ { item: 'it works!' } ], randominfo: 3 } }
// getValue(path, obj)
export const getValue = ( path , obj) => {
const newPath = path.replace(/\]/g, "")
const arrayPath = newPath.split(/[\[\.]+/) || newPath;
const final = arrayPath.reduce( (obj, k) => obj ? obj[k] : obj, obj)
return final;
}
如果你试图通过id或名称从示例结构中访问一个项,而不知道它在数组中的位置,最简单的方法是使用underscore.js库:
var data = {
code: 42,
items: [{
id: 1,
name: 'foo'
}, {
id: 2,
name: 'bar'
}]
};
_.find(data.items, function(item) {
return item.id === 2;
});
// Object {id: 2, name: "bar"}
根据我的经验,使用高阶函数而不是for或for..in循环会导致代码更容易推理,因此更易于维护。
这只是我的个人意见。
有时,使用字符串访问嵌套对象是可取的。例如,最简单的方法是第一级
var obj = { hello: "world" };
var key = "hello";
alert(obj[key]);//world
但复杂的json通常不是这样。随着json变得越来越复杂,在json中查找值的方法也变得越来越复杂。导航json的递归方法是最好的,如何利用递归取决于要搜索的数据类型。如果涉及到条件语句,json搜索可能是一个很好的工具。
如果已经知道要访问的属性,但是路径很复杂,例如在这个对象中
var obj = {
arr: [
{ id: 1, name: "larry" },
{ id: 2, name: "curly" },
{ id: 3, name: "moe" }
]
};
你知道你想要得到对象中数组的第一个结果,也许你想使用
var moe = obj["arr[0].name"];
然而,这将导致一个异常,因为对象没有该名称的属性。能够使用这种方法的解决方案是将对象的树形面平直。这可以递归完成。
function flatten(obj){
var root = {};
(function tree(obj, index){
var suffix = toString.call(obj) == "[object Array]" ? "]" : "";
for(var key in obj){
if(!obj.hasOwnProperty(key))continue;
root[index+key+suffix] = obj[key];
if( toString.call(obj[key]) == "[object Array]" )tree(obj[key],index+key+suffix+"[");
if( toString.call(obj[key]) == "[object Object]" )tree(obj[key],index+key+suffix+".");
}
})(obj,"");
return root;
}
现在,这个复杂的物体可以被平面化
var obj = previous definition;
var flat = flatten(obj);
var moe = flat["arr[0].name"];//moe
下面是使用这种方法的jsFiddle演示。