4

I have a parts list in the following structure:

level | description
    0 | sfg
    1 | sdf
    2 | asdisg
    3 | sidjhf
    4 | wefdsj
    4 | asdfg
    4 | sgfd
    4 | sdg
    3 | sfg
    3 | fdg
    4 | sdfg
    4 | sdsfd
    4 | sdf
    4 | sdf
    2 | adf
    3 | sdfg
    4 | sdg
    4 | sdf
    4 | sdf
    4 | sdf
    1 | shfg
    2 | ijsd
    3 | ijsd
    4 | sdf
    4 | sdf

What I need is to convert this part list into a hierarchy folder structure like this (prefered in nested JSON): enter image description here

I want to use the following structure in TypeScript:

export interface Foo {
  level: number;
  description: string;
  children?: Foo[];
}

What I need is a nested JSON object or something like a nested array in which the array contains children with another array.

Unfortunately I have only pseudocode to show (I know, this will never work):

  recursiveWalker(List, lastLevel, parent) {
    for (let i = 0; i < List.length; ++i) {
      const node = {
        description: List.description,
        level: List.level
      };
      if (List.level === lastLevel + 1) {
        node.children = this.recursiveWalker(List, lastLevel + 2, node);
      }
    }
    return node;
  }

My question is now: Is there a simple solution to create such nested data? Do I have to use recursive functions, or are there any algorithms which I can implement?

The goal is to create a material tree in Angular (https://material.angular.io/components/tree/overview) with this data.

I really appreciate any kind of help!

UPDATE: The following structure will be needed:

  const bar: Foo = {
    description: 'this is level 0 (root)',
    level: 0,
    children: [{
      description: 'this is level 1',
      level: 1,
      children: [
        {
          description: 'this is level 2',
          level: 2
        },
        {
          description: 'this is level 2',
          level: 2
        },
        {
          description: 'this is level 2',
          level: 2,
          children: [
            {
              description: 'this is level 3',
              level: 3
            },
            {
              description: 'this is level 3',
              level: 3
            },
            {
              description: 'this is level 3',
              level: 3,
              children: [] /* AND SO ON .... */
            }
          ]
        }
      ]
    }]
  };
});
2
  • 2
    how do you now which next level goes under which parent? please add a wanted data structure which matches the input data. Commented Nov 21, 2019 at 8:46
  • @NinaScholz in the same order as it comes. I will update my post. Commented Nov 21, 2019 at 8:50

1 Answer 1

3

You could take a lazy approach by taking an array levels as helper for keeping track of the latest nodes of the actual level.

var data = [{ level: 0, description: '0' }, { level: 1, description: '0-0' }, { level: 2, description: '0-0-0' }, { level: 3, description: '0-0-0-0' }, { level: 4, description: '0-0-0-0-0' }, { level: 4, description: '0-0-0-0-1' }, { level: 4, description: '0-0-0-0-2' }, { level: 4, description: '0-0-0-0-3' }, { level: 3, description: '0-0-0-1' }, { level: 3, description: '0-0-0-2' }, { level: 4, description: '0-0-0-2-0' }, { level: 4, description: '0-0-0-2-1' }, { level: 4, description: '0-0-0-2-2' }, { level: 4, description: '0-0-0-2-3' }, { level: 2, description: '0-0-1' }, { level: 3, description: '0-0-1-0' }, { level: 4, description: '0-0-1-0-0' }, { level: 4, description: '0-0-1-0-1' }, { level: 4, description: '0-0-1-0-2' }, { level: 4, description: '0-0-1-0-3' }, { level: 1, description: '0-1' }, { level: 2, description: '0-1-0' }, { level: 3, description: '0-1-0-0' }, { level: 4, description: '0-1-0-0-0' }, { level: 4, description: '0-1-0-0-1' }],
    tree = [],
    levels = [tree];
   
data.forEach(({ level, description }) =>
    levels[level].push({ level, description, children: levels[level + 1] = [] })
);

console.log(tree);
.as-console-wrapper { max-height: 100% !important; top: 0; }

Sign up to request clarification or add additional context in comments.

1 Comment

Oh thank you very much @NinaScholz! This is such a good approach. It works fine. I marked the answer as accepted. You saved my day :)

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.