0

I have an array of objects structured as below:

const myArr = [
   { name: "John", surname: "Smith", age: 18},
   { name: "Steve", surname: "Jones", age: 23},
   { name: "Mark", surname: "Green", age: 45},
   { name: "Anne", surname: "Williams", age: 34}
]

And I would like to group it like so:

[
   {name: ["John", "Steve", "Mark", "Anne"]},
   {surname: ["Smith", "Jones", "Green", "Williams"]},
   {age: [18, 23, 45, 34]}
]

What's the best way? Tried with reduce() but no luck.

Mauro74
  • 4,686
  • 15
  • 58
  • 80
  • Hey, looks like it's duplicated https://stackoverflow.com/questions/14446511/most-efficient-method-to-groupby-on-an-array-of-objects – Taras Kumpanenko Dec 22 '20 at 12:52
  • 1
    Does this answer your question? [How to group an array of objects by key](https://stackoverflow.com/questions/40774697/how-to-group-an-array-of-objects-by-key) – Md Sabbir Alam Dec 22 '20 at 12:55

4 Answers4

2

Assuming you know all objects have exactly the same keys, you can use Object.keys() function on the first element of the array, then iterate over the keys to create your objects

Object.keys(myArr[0]).map(key => {
    const obj = {}; // Probably a better way to do that
    obj[key] = myArr.map(item => item[key]);
    return obj;
});
Alexandre Senges
  • 1,474
  • 1
  • 13
  • 22
1

Nastier but shorter.

Object.keys(myArr[0]).map(key => ({ [key]: myArr.map(item => item[key]) }));
DedaDev
  • 4,441
  • 2
  • 21
  • 28
1

You could iterate the array, get all entries from the object and push to the array with the wanted key.

const
    array = [{ name: "John", surname: "Smith", age: 18 }, { name: "Steve", surname: "Jones", age: 23 }, { name: "Mark", surname: "Green", age: 45 }, { name: "Anne", surname: "Williams", age: 34 }],
    result = array.reduce((r, o) => {
        Object.entries(o).forEach(([k, v]) => (r[k] ??= []).push(v));
        return r;
    }, {});

console.log(result);
.as-console-wrapper { max-height: 100% !important; top: 0; }
Nina Scholz
  • 376,160
  • 25
  • 347
  • 392
0

Use forEach and build an object with keys and aggregate values in array.
Now, create the array from above object entries.

const process = (arr) => {
  const res = {};
  arr.forEach((item) =>
    Object.entries(item).forEach(([key, value]) =>
      (res[key] ??= []).push(value)
    )
  );
  return Object.entries(res).map(([key, value]) => ({ [key]: value }));
};

const myArr = [
  { name: "John", surname: "Smith", age: 18 },
  { name: "Steve", surname: "Jones", age: 23 },
  { name: "Mark", surname: "Green", age: 45 },
  { name: "Anne", surname: "Williams", age: 34 },
];

console.log(process(myArr));
Siva K V
  • 10,561
  • 2
  • 16
  • 29