var arr1 = [11, 12, 13];
var arr2 = [
{ id: 11, name: "name 1" },
{ id: 12, name: "name 2" },
{ id: 13, name: "name 3" },
{ id: 14, name: "name 4" },
];
I have this two arrays and in the second array want to leave items which id's equal to first array values. I mean this:
var newArray = [
{ id: 11, name: "name 1" },
{ id: 12, name: "name 2" },
{ id: 13, name: "name 3" },
];
What is most efficient way to do this?
CodePudding user response:
First, build an index by mapping each id to its corresponding object. The index object will have this structure:
{
'11': { id: 11, name: 'name 1' },
'12': { id: 12, name: 'name 2' },
'13': { id: 13, name: 'name 3' },
'14': { id: 14, name: 'name 4' }
}
This index can be built in a variety of ways, one of which is to use Object.fromEntries
. Object.fromEntries(arr2.map(obj => [obj.id, obj]))
.
Then map each id
in your arr1
to its corresponding object with a lookup in your index
object: index[id]
. That will look like arr1.map(id => index[id])
.
var arr1 = [11, 12, 13];
var arr2 = [
{ id: 11, name: "name 1" },
{ id: 12, name: "name 2" },
{ id: 13, name: "name 3" },
{ id: 14, name: "name 4" },
];
const index = Object.fromEntries(arr2.map(obj => [obj.id, obj]));
const result = arr1.map(id => index[id]);
console.log(result);
This approach is efficient because it does not perform a linear search for each item's index (no .includes
or .find
per entry is required). Instead, it leverages the hashtable lookup of a property in an object (which is more or less constant time). Overall this is O(N) instead of O(N^2).
Beware, there may more overhead in creating such an index for small values of N. But for larger values of N this will be better, and also will be better if there are multiple variations of arr1
objects to be used with a single arr2
.
CodePudding user response:
This is a simple filter accessing the item id
and checking if that id
is included in the first array.
var arr1 = [11, 12, 13];
var arr2 = [
{ id: 11, name: "name 1" },
{ id: 12, name: "name 2" },
{ id: 13, name: "name 3" },
{ id: 14, name: "name 4" },
];
var newArray = arr2.filter(item => arr1.includes(item.id));
console.log(newArray);
Edit: In the spirit of efficient execution, another approach:
var arr1 = [11, 12, 13];
var arr2 = [
{ id: 11, name: "name 1" },
{ id: 12, name: "name 2" },
{ id: 13, name: "name 3" },
{ id: 14, name: "name 4" },
];
var objIds = arr1.reduce((obj, item) => (obj[item] = true) && obj, {})
var newArray = arr2.filter(item => objIds[item.id]);
console.log(objIds, newArray)