1
let masterList=[{id:1,name:'Abc'},{id:2,name:'Def'},{id:3,name:'Ghi'}];
let selectedList=[2,3];

The desired result is to have

//desiredList=[{id:2,name:'Def'},{id:3,name:'Ghi'}]

Currently what I am doing is

     let parsedArray = [];
      masterList.forEach(mItem => {
            selectedList.forEach(sItem => {
                if (mItem.id === sItem) {
                    parsedArray.push(mItem);
                }
            });
        });
     desiredList=parsedArray

I do not find this method efficient when iterating over large arrays, is there any logic, any inbuilt javascript operators using which I can achieve the same?

7
  • how large is a large array in this case? Commented Jul 8, 2019 at 10:23
  • Do you want the code to shorter/simpler or you want to have a single loop instead of nested loops? Commented Jul 8, 2019 at 10:25
  • does the order matters? Commented Jul 8, 2019 at 10:26
  • @MaheerAli I'd say having a simpler code and having a simple loop is a win win situation. But, I'd primarily would want the code to be faster and effecient. Commented Jul 8, 2019 at 10:28
  • 2
    50 is not enough elements to worry about optimizing for performance. Unless you have numbers that specifically show otherwise, I'd focus on making the lookup readable and measure. Commented Jul 8, 2019 at 10:42

6 Answers 6

6

You could take a map with id as key and the object as value and map the wanted values from the map by mapping selectedList.

This approach uses the order from selectedList.

var masterList = [{ id: 1, name: 'Abc' }, { id: 2, name: 'Def' }, { id: 3, name: 'Ghi' }],
    selectedList = [2, 3],
    result = selectedList.map(Map.prototype.get, new Map(masterList.map(o => [o.id, o])));

console.log(result);

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

Comments

4

It should be a simple filter on the masterList:

masterList.filter(item => selectedList.includes(item.id));

2 Comments

OP said: "I do not find this method efficient when iterating over large arrays". I think by this OP means he wants a better solution regarding time complexity. He don't want short code I guess.
Until the OP defines what large is and what kind of timing they want, it is difficult to comment on performance. However, the OP did ask for natvie methods to do what they were doing.
4

You can use Array filter() to do this.

Demo:

let masterList=[{id:1,name:'Abc'},{id:2,name:'Def'},{id:3,name:'Ghi'}];
let selectedList=[2,3];

let desiredList = masterList.filter((val) => selectedList.includes(val.id));
console.log(desiredList)

Comments

3

You can first convert selectedList to Set and then use filter() method array of objects.

You can use Set.prototype.has to check whether the id of the objects exists in the set or not. And this method has O(1) time-complexity. So the time-complexity of the whole algorithm will be linear.

let masterList=[{id:1,name:'Abc'},{id:2,name:'Def'},{id:3,name:'Ghi'}];
let selectedList = [2,3];
let set = new Set(selectedList);

let res = masterList.filter(x => set.has(x.id));
console.log(res)

Comments

2

Turn the first array into an object indexed by id first, so you can look up the appropriate matching object in O(1) time, and then you can .map the selectedList:

const masterList=[{id:1,name:'Abc'},{id:2,name:'Def'},{id:3,name:'Ghi'}];
const selectedList=[2,3,4];

const masterById = masterList.reduce((a, obj) => {
  a[obj.id] = obj;
  return a;
}, {});

const desiredList = selectedList.map(id => masterById[id]).filter(Boolean);
console.log(desiredList);

Comments

2

Try this:

let masterList=[{id:1,name:'Abc'},{id:2,name:'Def'},{id:3,name:'Ghi'}];
let selectedList=[2,3];

const result = masterList.filter(({id})=> selectedList.includes(id));

console.log(result);

Comments

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.