Ridhwaan Shakeel
Ridhwaan Shakeel

Reputation: 1053

Javascript how do you sort an array of objects at the top level by nested object property

var originalArray = [
    {
        name: 'Store1',
        inventory: [
            { name: 'Oranges', qt: [{ id: "something", time: 11 }, { id: "something", time: 44 }, { id: "something", time: 53 }] },
            { name: 'Mango', qt: [{ id: "something", time: 3 }, { id: "something", time: 91 }, { id: "something", time: 3 }] },
            { name: 'Kiwi', qt: [{ id: "something", time: 2 }, { id: "something", time: 91 }, { id: "something", time: 3 }] },
            { name: 'Papaya', qt: [{ id: "something", time: 8 }, { id: "something", time: 91 }, { id: "something", time: 3 }] }
        ]
    },
    {
        name: 'Store2',
        inventory: [
            { name: 'Pizza', qt: [{ id: "something", time: 31 }, { id: "something", time: 11 }, { id: "something", time: 23 }] },
            { name: 'Burger', qt: [{ id: "something", time: 1 }, { id: "something", time: 11 }, { id: "something", time: 23 }] },
            { name: 'IceCream', qt: [{ id: "something", time: 111 }, { id: "something", time: 11 }, { id: "something", time: 323 }] }
        ]
    }
];

For example in the above array, inventory and qt are nested keys with an array of objects as their value.
Store2 has { id: "something", time: 323 } which is a higher time than any item in Store1
After sort, Store2 will be first in the list and Store1 will be in second position, and so on, time descending

My code is not working to sort the stores.
It should not sort the nested array in inventory & qt, just sort the Store order by time descending

const sorted = originalArray
  .map(store => store.inventory
  .map(inv => inv.qt
  .map(item => Object.entries(item)[1])))
  .sort((a, b) => b[1].time - a[1].time)
  .map(item => item[1])

console.log(JSON.stringify(sorted));

EXPECTED OUTPUT

// sorted array
[
    {
        name: 'Store2',
        inventory: [
            { name: 'Pizza', qt: [{ id: "something", time: 31 }, { id: "something", time: 11 }, { id: "something", time: 23 }] },
            { name: 'Burger', qt: [{ id: "something", time: 1 }, { id: "something", time: 11 }, { id: "something", time: 23 }] },
            { name: 'IceCream', qt: [{ id: "something", time: 111 }, { id: "something", time: 11 }, { id: "something", time: 323 }] }
        ]
    },
    {
        name: 'Store1',
        inventory: [
            { name: 'Oranges', qt: [{ id: "something", time: 11 }, { id: "something", time: 44 }, { id: "something", time: 53 }] },
            { name: 'Mango', qt: [{ id: "something", time: 3 }, { id: "something", time: 91 }, { id: "something", time: 3 }] },
            { name: 'Kiwi', qt: [{ id: "something", time: 2 }, { id: "something", time: 91 }, { id: "something", time: 3 }] },
            { name: 'Papaya', qt: [{ id: "something", time: 8 }, { id: "something", time: 91 }, { id: "something", time: 3 }] }
        ]
    }
]

Upvotes: 0

Views: 104

Answers (2)

anotherOne
anotherOne

Reputation: 1573

This should work:

const highestTime = (inventory) => {
  let max = 0;
  for (const item of inventory) {
    for (const obj of item.qt) {
      if (obj.time > max) max = obj.time;
    }
  }
  return max;
};

const sortedArray = originalArray.sort((a, b) => highestTime(b.inventory) - highestTime(a.inventory));

Upvotes: 1

Bravo
Bravo

Reputation: 6264

This isn't the most efficient way, but it does the job

var originalArray = [
    {
        name: 'Store1',
        inventory: [
            { name: 'Oranges', qt: [{ id: "something", time: 11 }, { id: "something", time: 44 }, { id: "something", time: 53 }] },
            { name: 'Mango', qt: [{ id: "something", time: 3 }, { id: "something", time: 91 }, { id: "something", time: 3 }] },
            { name: 'Kiwi', qt: [{ id: "something", time: 2 }, { id: "something", time: 91 }, { id: "something", time: 3 }] },
            { name: 'Papaya', qt: [{ id: "something", time: 8 }, { id: "something", time: 91 }, { id: "something", time: 3 }] }
        ]
    },
    {
        name: 'Store2',
        inventory: [
            { name: 'Pizza', qt: [{ id: "something", time: 31 }, { id: "something", time: 11 }, { id: "something", time: 23 }] },
            { name: 'Burger', qt: [{ id: "something", time: 1 }, { id: "something", time: 11 }, { id: "something", time: 23 }] },
            { name: 'IceCream', qt: [{ id: "something", time: 111 }, { id: "something", time: 11 }, { id: "something", time: 323 }] }
        ]
    }
];
const sorted = originalArray.slice().sort((a, b) => {
    maxA = Math.max(...a.inventory.flatMap(({qt})=>qt.map(({time})=>time)));
    maxB = Math.max(...b.inventory.flatMap(({qt})=>qt.map(({time})=>time)));
    return maxB-maxA
});
console.log(sorted);

Upvotes: 1

Related Questions