kurakuramikan
kurakuramikan

Reputation: 13

How to get parent id in unlimited nested array in JavaScript

It is as the title, but I am facing a problem!

I want to create getParentId(array, id) function.

This function get parent id by child id.

const array = [{
  id: 1,
  title: 'hello',
  children: [{
    id: 3,
    title: 'hello',
    children: [{
      id: 4,
      title:'hello',
      children: [
        { id: 5, title: 'hello'},
        { id: 6, title: 'hello'}
      ]
    },
    {
      id: 7,
      title: 'hello'
    }]
  }]
},
{
  id: 2,
  title: 'hello',
  children: [
    { id: 8, title: 'hello'}
  ]
}]

Expected Result:

getParentId(array, 3) -> 1

getParentId(array, 5) -> 4

getParentId(array, 6) -> 4

getParentId(array, 8) -> 2

getParentId(array, 2) -> null

I would be grateful if you would send me information.

Upvotes: 1

Views: 1386

Answers (2)

Nina Scholz
Nina Scholz

Reputation: 386746

You could take a recursive approach by iterating the actual array and their children and stop if the id is found.

function getParentId(array, id, parentId = null) {
    return array.some(o => {
        if (o.id === id) return true;
        const temp = getParentId(o.children || [], id, o.id);
        if (temp !== null) {
            parentId = temp;
            return true;
        }
    })
        ? parentId
        : null;
}

const array = [{ id: 1, title: 'hello', children: [{ id: 3, title: 'hello', children: [{ id: 4, title:'hello', children: [{ id: 5, title: 'hello' }, { id: 6, title: 'hello' }] }, { id: 7, title: 'hello' }] }] }, { id: 2, title: 'hello', children: [{ id: 8, title: 'hello' }] }];

console.log(getParentId(array, 3)); // 1
console.log(getParentId(array, 5)); // 4
console.log(getParentId(array, 6)); // 4
console.log(getParentId(array, 8)); // 2
console.log(getParentId(array, 2)); // null
console.log(getParentId(array, 7)); // 3
console.log(getParentId(array, 4)); // 3
.as-console-wrapper { max-height: 100% !important; top: 0; }

Upvotes: 2

Jeto
Jeto

Reputation: 14927

Nina Scholz's answer is great, but here's a slightly less functional approach (not using Array.some), if you like it better:

const array = [{id: 1, title: 'hello', children: [{id: 3, title: 'hello', children: [{id: 4, title:'hello', children: [{ id: 5, title: 'hello'}, { id: 6, title: 'hello'}]}, {id: 7, title: 'hello'}]}]}, {id: 2, title: 'hello', children: [{ id: 8, title: 'hello'}]}];

function getParentId(array, id, parentId = null) {
  // For every entry in the array
  for (const entry of array) {
    // If the ID matches, return the current parent ID
    if (entry.id === id) {
      return parentId;
    }
    // Otherwise, call the same function on its children, passing itself as the parent.
    // If there was a match, return it.
    if (entry.children && (deeperParentId = getParentId(entry.children, id, entry.id))) {
      return deeperParentId;
    }
  }
  // No match was found
  return null;
}

console.log(getParentId(array, 3));
console.log(getParentId(array, 5));
console.log(getParentId(array, 6));
console.log(getParentId(array, 8));
console.log(getParentId(array, 2));

Note that I overcommented it, which is not such a good idea when writing actual code; this is just for the answer.

Also, as I mentioned in the comments, please share your attempts next time.

Upvotes: 1

Related Questions