Здравствуйте, я пытаюсь выяснить, как получить объект с определенным идентификатором из массива с несколькими уровнями. Массив будет иметь объекты, эти объекты могут иметь массивы с объектами в качестве значений. Например, см. Данные, приведенные ниже:

[
    {
        "id": "e1f015d3-4ca8-4dfd-839d-bed9bbbb82f8",
        "text": "Parent Menu 2",
        "icon": "e1f015d3-4ca8-4dfd-839d-bed9bbbb82f8/rose-3142529__340.jpg",
        "page_type": "parent_menu",
        "data": "e1f015d3-4ca8-4dfd-839d-bed9bbbb82f8",
        "ui_config": "",
        "order": 2
    },
    {
        "id": "5bc4ff1a-69b5-496b-a484-0aa99b886122",
        "text": "Home",
        "icon": "5bc4ff1a-69b5-496b-a484-0aa99b886122/1024x1024.png",
        "page_type": "parent_menu",
        "is_homepage": true,
        "data": "5bc4ff1a-69b5-496b-a484-0aa99b886122",
        "ui_config": "",
        "order": 1,
        "submenus": [
            {
                "id": "4960a54c-6d27-4d8d-a272-ebc7d9e8a55e",
                "text": "Grid Menu",
                "icon": "4960a54c-6d27-4d8d-a272-ebc7d9e8a55e/rose-3142529__340.jpg",
                "page_type": "grid_menu",
                "data": "4960a54c-6d27-4d8d-a272-ebc7d9e8a55e",
                "ui_config": "",
                "order": 1,
                "submenus": [
                    {
                        "id": "906cd86f-df57-4175-a2c6-ca3a5c724e8a",
                        "text": "Article Page 2",
                        "icon": "906cd86f-df57-4175-a2c6-ca3a5c724e8a/rose-3142529__340.jpg",
                        "page_type": "article_page",
                        "data": "{\"page_id\":\"3e025c87-1d03-46a6-800e-0a9daea52bf4\"}",
                        "ui_config": "",
                        "order": 2
                    },
                    {
                        "id": "da8b054a-274e-4e1b-9d5a-e058a934838b",
                        "text": "Article Page",
                        "icon": "da8b054a-274e-4e1b-9d5a-e058a934838b/rose-3142529__340.jpg",
                        "page_type": "article_page",
                        "data": "{\"page_id\":\"3e025c87-1d03-46a6-800e-0a9daea52bf4\"}",
                        "ui_config": "",
                        "order": 1
                    }
                ]
            }
        ]
    }
]

Допустим, мне нужно получить объект с идентификатором da8b054a-274e-4e1b-9d5a-e058a934838b. Как мне это сделать?

Вот рекурсивная функция, которую я написал для этого:

var currentMenuItem = null
function getTheCurrentMenu(menu, id) {
  if (currentMenuItem != null) {
    return
  }
  if (!Array.isArray(menu)) {
    if (menu.id == id) {
      currentMenuItem = menu
      return
    }
  }
  for (var item in menu) {
    console.log(item)
    getTheCurrentMenu(item, id)
  }
}

Это делает браузер не отвечающим и выдает ошибку too much recursion.

Может кто-нибудь помочь мне с этим?

1
defiant 2 Май 2019 в 10:35

3 ответа

Лучший ответ

Вы можете сделать это с помощью метода reduce и установить аккумулятор в текущий элемент, если идентификатор совпадает.

const data = [{"id":"e1f015d3-4ca8-4dfd-839d-bed9bbbb82f8","text":"Parent Menu 2","icon":"e1f015d3-4ca8-4dfd-839d-bed9bbbb82f8/rose-3142529__340.jpg","page_type":"parent_menu","data":"e1f015d3-4ca8-4dfd-839d-bed9bbbb82f8","ui_config":"","order":2},{"id":"5bc4ff1a-69b5-496b-a484-0aa99b886122","text":"Home","icon":"5bc4ff1a-69b5-496b-a484-0aa99b886122/1024x1024.png","page_type":"parent_menu","is_homepage":true,"data":"5bc4ff1a-69b5-496b-a484-0aa99b886122","ui_config":"","order":1,"submenus":[{"id":"4960a54c-6d27-4d8d-a272-ebc7d9e8a55e","text":"Grid Menu","icon":"4960a54c-6d27-4d8d-a272-ebc7d9e8a55e/rose-3142529__340.jpg","page_type":"grid_menu","data":"4960a54c-6d27-4d8d-a272-ebc7d9e8a55e","ui_config":"","order":1,"submenus":[{"id":"906cd86f-df57-4175-a2c6-ca3a5c724e8a","text":"Article Page 2","icon":"906cd86f-df57-4175-a2c6-ca3a5c724e8a/rose-3142529__340.jpg","page_type":"article_page","data":"{\"page_id\":\"3e025c87-1d03-46a6-800e-0a9daea52bf4\"}","ui_config":"","order":2},{"id":"da8b054a-274e-4e1b-9d5a-e058a934838b","text":"Article Page","icon":"da8b054a-274e-4e1b-9d5a-e058a934838b/rose-3142529__340.jpg","page_type":"article_page","data":"{\"page_id\":\"3e025c87-1d03-46a6-800e-0a9daea52bf4\"}","ui_config":"","order":1}]}]}]

function get(data, id) {
  return data.reduce((r, e) => {
    if(e.id === id) r = e;
    if(!r && e.submenus) return get(e.submenus, id)
    return r;
  }, null)
}

const result = get(data, 'da8b054a-274e-4e1b-9d5a-e058a934838b');
console.log(result)
3
Nenad Vracar 2 Май 2019 в 07:48
var data = `
[
    {
        "id": "e1f015d3-4ca8-4dfd-839d-bed9bbbb82f8",
        "text": "Parent Menu 2",
        "icon": "e1f015d3-4ca8-4dfd-839d-bed9bbbb82f8/rose-3142529__340.jpg",
        "page_type": "parent_menu",
        "data": "e1f015d3-4ca8-4dfd-839d-bed9bbbb82f8",
        "ui_config": "",
        "order": 2
    },
    {
        "id": "5bc4ff1a-69b5-496b-a484-0aa99b886122",
        "text": "Home",
        "icon": "5bc4ff1a-69b5-496b-a484-0aa99b886122/1024x1024.png",
        "page_type": "parent_menu",
        "is_homepage": true,
        "data": "5bc4ff1a-69b5-496b-a484-0aa99b886122",
        "ui_config": "",
        "order": 1,
        "submenus": [
            {
                "id": "4960a54c-6d27-4d8d-a272-ebc7d9e8a55e",
                "text": "Grid Menu",
                "icon": "4960a54c-6d27-4d8d-a272-ebc7d9e8a55e/rose-3142529__340.jpg",
                "page_type": "grid_menu",
                "data": "4960a54c-6d27-4d8d-a272-ebc7d9e8a55e",
                "ui_config": "",
                "order": 1,
                "submenus": [
                    {
                        "id": "906cd86f-df57-4175-a2c6-ca3a5c724e8a",
                        "text": "Article Page 2",
                        "icon": "906cd86f-df57-4175-a2c6-ca3a5c724e8a/rose-3142529__340.jpg",
                        "page_type": "article_page",
                        "ui_config": "",
                        "order": 2
                    },
                    {
                        "id": "da8b054a-274e-4e1b-9d5a-e058a934838b",
                        "text": "Article Page",
                        "icon": "da8b054a-274e-4e1b-9d5a-e058a934838b/rose-3142529__340.jpg",
                        "page_type": "article_page",
                        "ui_config": "",
                        "order": 1
                    }
                ]
            }
        ]
    }
]`;


var menu = JSON.parse(data);

async function getTheCurrentMenu(menu, id) {
  if (!Array.isArray(menu)) {
    if (menu.id == id) {
      return menu;
    } else if(menu.submenus){
      return getTheCurrentMenu(menu.submenus, id);
    } else {
      return;
    }
  }
  for (let item of menu) {
    console.log(item)
    let result = await getTheCurrentMenu(item, id);
    if(result != null) {
      return result;
    }
  }
}

getTheCurrentMenu(menu, 'da8b054a-274e-4e1b-9d5a-e058a934838b').then((item) => {
  console.log("Result: ", item);
})
0
Wendelin 2 Май 2019 в 07:53

Вы можете выполнить итеративный и рекурсивный вызов с коротким замыканием, если элемент найден.

function find(array, id) {
    var item;
    for (item of array) {
        if (item.id === id) return item;
        if (item.submenus && (item = find(item.submenus, id))) return item;
    }
}

var data = [{ id: "e1f015d3-4ca8-4dfd-839d-bed9bbbb82f8", text: "Parent Menu 2", icon: "e1f015d3-4ca8-4dfd-839d-bed9bbbb82f8/rose-3142529__340.jpg", page_type: "parent_menu", data: "e1f015d3-4ca8-4dfd-839d-bed9bbbb82f8", ui_config: "", order: 2 }, { id: "5bc4ff1a-69b5-496b-a484-0aa99b886122", text: "Home", icon: "5bc4ff1a-69b5-496b-a484-0aa99b886122/1024x1024.png", page_type: "parent_menu", is_homepage: true, data: "5bc4ff1a-69b5-496b-a484-0aa99b886122", ui_config: "", order: 1, submenus: [{ id: "4960a54c-6d27-4d8d-a272-ebc7d9e8a55e", text: "Grid Menu", icon: "4960a54c-6d27-4d8d-a272-ebc7d9e8a55e/rose-3142529__340.jpg", page_type: "grid_menu", data: "4960a54c-6d27-4d8d-a272-ebc7d9e8a55e", ui_config: "", order: 1, submenus: [{ id: "906cd86f-df57-4175-a2c6-ca3a5c724e8a", text: "Article Page 2", icon: "906cd86f-df57-4175-a2c6-ca3a5c724e8a/rose-3142529__340.jpg", page_type: "article_page", data: "{\"page_id\":\"3e025c87-1d03-46a6-800e-0a9daea52bf4\"}", ui_config: "", order: 2 }, { id: "da8b054a-274e-4e1b-9d5a-e058a934838b", text: "Article Page", icon: "da8b054a-274e-4e1b-9d5a-e058a934838b/rose-3142529__340.jpg", page_type: "article_page", data: "{\"page_id\":\"3e025c87-1d03-46a6-800e-0a9daea52bf4\"}", ui_config: "", order: 1 }] }] }],
    id = 'da8b054a-274e-4e1b-9d5a-e058a934838b',
    result = find(data, id);

console.log(result);
4
Nina Scholz 2 Май 2019 в 07:57