Home > Net >  Create an array of nested objects from an array of arrays
Create an array of nested objects from an array of arrays

Time:10-31

I'm trying to convert an array of arrays into an array of nested objects in JavaScript. Let's assume each subarray in the array represents a file path. I want to create an array of objects where each object has 2 properties, the name of the current file and any files/children that come after the current file/parent.

So for example, if I have this array of arrays where each subarray represents a file path:

[['A', 'B', 'C'], ['A', 'B', 'D'], ['L', 'M', 'N']]

I want to get this as the result:

[
  {
    name :'A',
    children: [
      {
        name: 'B',
        children: [
          {
            name: 'C',
            children: []
          },
          {
            name: 'D',
            children: []
          }
        ]
      }
    ]
  },
  {
    name: 'L',
    children: [
      {
        name: 'M',
        children: [
          {
            name: 'N',
            children: []
          }
        ]
      }
    ]
  }
]

I tried mapping through the array of arrays and creating an object for the current file/parent if it hasn't been created yet. I think I may be on the right track but I can't seem to think of the best way to do so.

CodePudding user response:

Something I could do in 5 minutes, it probably can be improved. This could also be written as a recursive function, I believe.

const result = [];

arr.forEach((subArr) => {
  var ref = result;
  subArr.forEach((name) => {
    const obj = ref.find((obj) => obj.name == name);
    if (obj) {
      ref = obj.children;
    } else {
      ref.push({ name, children: [] });
      ref = ref[ref.length - 1].children;
    }
  });
});

CodePudding user response:

Here's mine:

// Function to convert path array ‘a’ from position ‘i’ into tree structure in ‘v’.
const tree = (a, i, v) => {
    if (i < a.length) { tree(a, i 1, v[a[i]] ||= { }) }
}

// Function to convert a simple node into the desired record format.
const record = (v) => {
    const a = [];
    for (const [k, w] of Object.entries(v)) {
        a.push({ name: k, children: record(w) });
    }
    return a;
}

const m = { }
for (const a of [['A', 'B', 'C'], ['A', 'B', 'D'], ['L', 'M', 'N']]) {
    tree(a, 0, m);
}
const result = record(m);
  • Related