2017-09-02 94 views
0

我有一个像下面的结构;Javascript从其他值获取多维数组对象的值

var devices = { 
    'device-1' : { 
     'id' :'device1', 
     'template' :'template-1', 
     'user-1' :{ 
     'name' : 'John Doe', 
     'authority' : 'author1', 
     }, 
     'admin-1' :{ 
     'name' : 'Bob Doe', 
     'authority' : 'author2', 
     }, 
     'user-35' :{ 
     'name' : 'Bill Doe', 
     'authority' : 'author1', 
     }, 
     'author-42' :{ 
     'name' : 'Jack Doe', 
     'authority' : 'author1|author3', 
     } 
    }, 
    'device-2' : { 
     'id' :'device2', 
     'template' :'template-2', 
     'some-27' :{ 
     'name' : 'John Doe', 
     'authority' : 'author1', 
     }, 
     'other-42' :{ 
     'name' : 'Jack Doe', 
     'authority' : 'author2', 
     } 
    }, 
    'device-7' : { 
     'id' :'device7', 
     'template' :'template-1', 
     'user-2' :{ 
     'name' : 'Samantha Doe', 
     'authority' : 'author2', 
     } 
     'admin-40' :{ 
     'name' : 'Marry Doe', 
     'authority' : 'author1', 
     }, 
    } 

}; 

我想通过过滤它们的'属性'值来获取user-x元素的所有'value'条目。

例如,

我想根据他们的'权威'属性过滤所有用户的名字(不管在哪个设备和哪些用户ID),并获得'John Doe','Bill Doe','Jack Doe','Marry Doe'(作为一个数组),如果我想筛选'author1 '权威',这样我就可以得到哪些用户在任何设备上拥有'author1'权限。

我检查了很多地方(包括StackOverflow),但大多数例子都限于二维对象数组,变量是特定的或对象是基于整数(如[0] => Array)。

但在这个例子中,'device-x''user-x'项是不确定的(所以我不能说他们的价值观是这些),但'name''authority'键是某些(由系统分配)和这些变量的数量可以改变(CRUD操作)。

谢谢你。

UPDATE:由于我的假设错误(我认为如果我编写不同的用户x部分,人们认为这些值不遵循任何规则)问题并不清楚。所以我编写了代码。 最后:'name'和'authority'键值对的所有者是用户名,它们是用户定义的。因此,所有设备对象都有id,模板,未知用户字段,但所有未知用户字段都必须具有“名称”和“权限”键值对。

+0

这里是你的代码? –

+0

我想用这个:https://stackoverflow.com/questions/2722159/javascript-how-to-filter-object-array-based-on-attributes,但不能成功呢。 因为,虽然引用的QA基于二维数组,但我无法实现子变量。 – Alper

回答

1

使用reduce & filter & map

更新:我添加了一个isLikeUserObj功能probs为name & authority领域。

const devices = { 
 
    'device-1': { 
 
    'id': 'device1', 
 
    'template': 'template-1', 
 
    'user-1': { 
 
     'name': 'John Doe', 
 
     'authority': 'author1', 
 
    }, 
 
    'admin-1': { 
 
     'name': 'Bob Doe', 
 
     'authority': 'author2', 
 
    }, 
 
    'user-35': { 
 
     'name': 'Bill Doe', 
 
     'authority': 'author1', 
 
    }, 
 
    'author-42': { 
 
     'name': 'Jack Doe', 
 
     'authority': 'author1|author3', 
 
    } 
 
    }, 
 
    'device-2': { 
 
    'id': 'device2', 
 
    'template': 'template-2', 
 
    'some-27': { 
 
     'name': 'John Doe', 
 
     'authority': 'author1', 
 
    }, 
 
    'other-42': { 
 
     'name': 'Jack Doe', 
 
     'authority': 'author2', 
 
    } 
 
    }, 
 
    'device-7': { 
 
    'id': 'device7', 
 
    'template': 'template-1', 
 
    'user-2': { 
 
     'name': 'Samantha Doe', 
 
     'authority': 'author2', 
 
    }, 
 
    'admin-40': { 
 
     'name': 'Marry Doe', 
 
     'authority': 'author1', 
 
    }, 
 
    } 
 
}; 
 

 
const result = getUserByAuthority('author3'); 
 

 
function getUserByAuthority(requiredAuth) { 
 
    return Object.keys(devices).reduce((result, deviceKey) => { 
 
    const users = Object.keys(devices[deviceKey]) 
 
     .filter((key) => isUserLikeObj(devices[deviceKey][key])) 
 
     .map(userKey => devices[deviceKey][userKey]) 
 
     .filter((user) => user.authority.split('|').indexOf(requiredAuth) > -1) 
 
     .map((user) => user.name) 
 
    return result.concat(users); 
 
    }, []) 
 
} 
 

 
function isUserLikeObj(value) { 
 
    return typeof value === 'object' && value.hasOwnProperty('name') && value.hasOwnProperty('authority') 
 
} 
 

 
console.log(result)

+0

感谢您的回答,请您检查问题更新 – Alper

+0

设备对象是否会包含id,'template','unknown-user-field'? – felixmosh

+0

是的,确切地说。但所有未知用户字段必须具有“名称”和“权限”键值对。 – Alper

0

您可以使用for-in循环遍历一个对象。以下方法可以实现你的需求

const result = [] 

for (let i in devices) { 
    for (let j in devices[i]) { 
    if (/user-\d+/.test(j)) { 
     if (devices[i][j].authority.split('|').indexOf('author1') !== -1) { 
     result.push(devices[i][j].name) 
     } 
    } 
    } 
} 

console.log(result) 
+0

感谢您的回答,请您检查问题更新 – Alper