skip to Main Content

I have an array of objects such as this:

var arr = [
    {name:"item1", category:0},
    {name:"item2", category:3},
    {name:"item3", category:1},
    {name:"item4", category:1},
]

I want to produce a multi-dimensional array based on category values such as this: (We can assume fixed length, i.e. no category 4)

var arr2 = [
    [{name:"item1", category:0}],
    [{name:"item3", category:1},{name:"item4", category:1}],
    [],
    [{name:"item2", category:3}]
]

My current solution is this:

var arr2 = [[],[],[],[]];
arr.forEach(x => {
    arr2[x.category].push(x);
});

But I’m looking for a more JavaScript-y way (with map, filter etc) and preferrably a one-liner.

Thanks for any help!

2

Answers


  1. you can try this code

    var arr = [
        {name:"item1", category:0},
        {name:"item2", category:3},
        {name:"item3", category:1},
        {name:"item4", category:1},
    ]
    
    let hashMap = new Map()
    
    arr.map(e => {
        if(hashMap.get(e.category) === undefined){
            hashMap.set(e.category, [e])
        }
        else{
            // because array will refered by address
            hashMap.get(e.category).push(e)
        }
    });
    
    console.log(hashMap)
    
    console.log(hashMap.values())
    
    console.log( Array.from(hashMap.values()) )
    

    Output

    Map(3) {
      0 => [ { name: 'item1', category: 0 } ],
      3 => [ { name: 'item2', category: 3 } ],
      1 => [ { name: 'item3', category: 1 }, { name: 'item4', category: 1 } ]
    }
    --------------
    [Map Iterator] {
      [ { name: 'item1', category: 0 } ],
      [ { name: 'item2', category: 3 } ],
      [ { name: 'item3', category: 1 }, { name: 'item4', category: 1 } ]
    }
    --------------
    [
      [ { name: 'item1', category: 0 } ],
      [ { name: 'item2', category: 3 } ],
      [ { name: 'item3', category: 1 }, { name: 'item4', category: 1 } ]
    ]
    
    Login or Signup to reply.
  2. Your one-liner: create an array with Array.from() with length of maximum category ID plus 1, and map elements with filtered arrays by the index category :

    var arr = [
        {name:"item1", category:0},
        {name:"item2", category:3},
        {name:"item3", category:1},
        {name:"item4", category:1},
    ]
    
    const result = Array.from({length: Math.max(...arr.map(item => item.category)) + 1}, (_, idx) => arr.filter(({category}) => category === idx));
    
    console.log(result);
    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search