javascript - 如何在数组 JavaScript 中查找嵌套对象的道具?
问题描述
我有一个看起来像这样的对象数组:
const roles = [
{
"id": "833ffe3d-cc24-4157-966c-5f8ceb856f4e",
"hidden": false,
"modified": "2020-03-20T15:14:12.689Z",
"label": "Solution 2",
"shortname": "Solution 2",
"description": "Solution 2 description",
"className": "Solution",
"children": [
{
"id": "f1708329-eb9f-4042-bbe7-cdd1ff41b1b7",
"hidden": false,
"modified": "2020-03-20T15:14:12.293Z",
"label": "USER CUSTOM ROLE",
"displayName": "USER CUSTOM ROLE DISPLAY NAME",
"className": "Role"
}
]
},
{
"id": "1a36709f-4de2-4f93-bf8e-57811d36e9f3",
"hidden": false,
"modified": "2020-03-20T15:14:12.668Z",
"label": "Solution 1",
"shortname": "Solution 1",
"description": "Solution 1 description",
"className": "Solution",
"children": [
{
"id": "e824afbd-8b19-4363-b6fa-dd604f445cef",
"hidden": false,
"modified": "2020-03-20T15:14:12.271Z",
"label": "USER ROLE",
"displayName": "USER ROLE DISPLAY NAME",
"className": "Role"
},
{
"id": "8f2600d0-5328-4d41-8270-2eb10541860f",
"hidden": false,
"modified": "2020-03-20T15:14:12.095Z",
"label": "BASE LOGIN ROLE",
"displayName": "DISPLAY NAME - BASE LOGIN ROLE",
"className": "Role"
},
{
"id": "a14ce471-b792-4a5d-95ad-b9abb5dbe45c",
"hidden": false,
"modified": "2020-03-20T15:14:12.102Z",
"label": "ORGANIZATION GLOBAL ROLE",
"displayName": "DISPLAY NAME - GLOBAL ROLE",
"className": "Role"
},
{
"id": "d4a7d6ac-1663-48be-9fed-ce2a908f28f1",
"hidden": false,
"modified": "2020-03-20T15:14:12.130Z",
"label": "DEPARTMENT 1 ROLE",
"className": "Role"
}
]
}
];
我关心的是这些对象的id、label和children。如您所见,一些角色对象包含它们自己的角色数组。我还有另一个选定的角色数组,如下所示:
const selected = ["Solution 1", "USER ROLE", "DEPARTMENT 1 ROLE"];
我想要的是创建与所选角色相对应的平面 ID 数组,例如,对于这个选定的数组,它将是(顺序不重要):
const result = ["d4a7d6ac-1663-48be-9fed-ce2a908f28f1", "e824afbd-8b19-4363-b6fa-dd604f445cef", "1a36709f-4de2-4f93-bf8e-57811d36e9f3"];
所以我的伪代码算法是: 1. 检查根级对象。2.如果它的标签在选定的数组中,将它的id推送到结果数组。3. 如果它有 children 道具,检查它所有的孩子是否相同。4. 对所有其他对象重复此操作。
我自己只能想出非常臭的功能,它仍然不能解决嵌套角色的问题。我的功能是:
function getIds(arr, names) {
let result = [];
for (let i = 0; i < arr.length; i++) {
for (let j = 0; j < names.length; j++) {
if (arr[i].label == names[j]) {
result.push(arr[i].id);
}
if (arr[i].children) {
for (let k = 0; k < arr[i].children.length; k++) {
if (arr[i].children[k].label == names[j]) {
result.push(arr[i].children[k].id);
}
}
}
}
}
return result;
}
我知道,还有更清洁、更漂亮的解决方案,我就是想不出一个。你能帮我吗?
解决方案
首先,我将使用.flatMap()
. 然后只需.map()
将标签与数组元素匹配并返回 id。
尝试以下操作:
const selected = ["Solution 1", "USER ROLE", "DEPARTMENT 1 ROLE"];
const roles = [{ "id": "833ffe3d-cc24-4157-966c-5f8ceb856f4e", "hidden": false, "modified": "2020-03-20T15:14:12.689Z", "label": "Solution 2", "shortname": "Solution 2", "description": "Solution 2 description", "className": "Solution", "children": [{ "id": "f1708329-eb9f-4042-bbe7-cdd1ff41b1b7", "hidden": false, "modified": "2020-03-20T15:14:12.293Z", "label": "USER CUSTOM ROLE", "displayName": "USER CUSTOM ROLE DISPLAY NAME", "className": "Role" } ] }, { "id": "1a36709f-4de2-4f93-bf8e-57811d36e9f3", "hidden": false, "modified": "2020-03-20T15:14:12.668Z", "label": "Solution 1", "shortname": "Solution 1", "description": "Solution 1 description", "className": "Solution", "children": [{ "id": "e824afbd-8b19-4363-b6fa-dd604f445cef", "hidden": false, "modified": "2020-03-20T15:14:12.271Z", "label": "USER ROLE", "displayName": "USER ROLE DISPLAY NAME", "className": "Role" }, { "id": "8f2600d0-5328-4d41-8270-2eb10541860f", "hidden": false, "modified": "2020-03-20T15:14:12.095Z", "label": "BASE LOGIN ROLE", "displayName": "DISPLAY NAME - BASE LOGIN ROLE", "className": "Role" }, { "id": "a14ce471-b792-4a5d-95ad-b9abb5dbe45c", "hidden": false, "modified": "2020-03-20T15:14:12.102Z", "label": "ORGANIZATION GLOBAL ROLE", "displayName": "DISPLAY NAME - GLOBAL ROLE", "className": "Role" }, { "id": "d4a7d6ac-1663-48be-9fed-ce2a908f28f1", "hidden": false, "modified": "2020-03-20T15:14:12.130Z", "label": "DEPARTMENT 1 ROLE", "className": "Role" } ] } ];
const flat = roles.flatMap(e => e.children.concat(e));
const result = selected.map(e => flat.find(f => f.label === e).id);
console.log(selected);
console.log(result);
我希望这有帮助!
推荐阅读
- apache-spark - 如何在 Kubernetes 上向 Spark 发送作业。无法实例化外部调度程序
- tmux - 如果客户端的屏幕尺寸太小,有没有办法拒绝客户端连接到 tmux?
- xcode - 如何防止 CI 因构建编号冲突而陷入循环?
- tfs - TFS 搁置集/门控签入失败:TF400898:发生内部错误
- ruby-on-rails - 如何修改文件的目录名/路径?
- ios - SIGSEGV 崩溃:com.apple.root.default-qos
- cairo - 很棒的 WM:径向渐变是如何工作的
- python - .loc[index, col] 和 .loc[index][col] 有什么区别?
- python - How to make new window in pygame?
- android - Kotlin/Java 继承和接口