I have an array like this:
[{prop1:"abc",prop2:"qwe"},{prop1:"abc",prop2:"yutu"},{prop1:"xyz",prop2:"qwrq"}]
I'd like to get the index of all elements that satisfy a condition; in this case, when prop1 == "abc"
. So the desired output is something like [0,1]
.
Struggling to find a clean way of doing this?
indexes = a.findIndex(x => x.prop1==="abc")
will return 0
for the above array, because it stops at the first successful find.
I feel like I want something like this: indexes = a.filtered(x.index() => x.prop1==="abc")
I have an array like this:
[{prop1:"abc",prop2:"qwe"},{prop1:"abc",prop2:"yutu"},{prop1:"xyz",prop2:"qwrq"}]
I'd like to get the index of all elements that satisfy a condition; in this case, when prop1 == "abc"
. So the desired output is something like [0,1]
.
Struggling to find a clean way of doing this?
indexes = a.findIndex(x => x.prop1==="abc")
will return 0
for the above array, because it stops at the first successful find.
I feel like I want something like this: indexes = a.filtered(x.index() => x.prop1==="abc")
5 Answers
Reset to default 13You can use Array#reduce
method.
var data = [{prop1:"abc",prop2:"qwe"},{prop1:"abc",prop2:"yutu"},{prop1:"xyz",prop2:"qwrq"}];
console.log(
data.reduce(function(arr, e, i) {
if (e.prop1 == 'abc') arr.push(i);
return arr;
}, [])
)
// with ES6 arrow syntax
console.log(
data.reduce((arr, e, i) => ((e.prop1 == 'abc') && arr.push(i), arr), [])
)
With simple for
loop
var data = [{prop1:"abc",prop2:"qwe"},{prop1:"abc",prop2:"yutu"},{prop1:"xyz",prop2:"qwrq"}];
var res = [];
for (var i = 0; i < data.length; i++) {
if (data[i].prop1 == 'abc') res.push(i);
}
console.log(res)
Or use Array#filter
with Array#map
method(Not an efficient way since it needs to iterate twice).
var data = [{prop1:"abc",prop2:"qwe"},{prop1:"abc",prop2:"yutu"},{prop1:"xyz",prop2:"qwrq"}];
console.log(
data.map(function(e, i) {
return i;
}).filter(function(e) {
return data[e].prop1 == 'abc';
})
)
// With ES6 arrow syntax
console.log(
data.map((_, i) => i).filter(e => data[e].prop1 == 'abc')
)
You can use reduce
function.
var array = [{ prop1: "abc", prop2: "qwe" },
{ prop1: "abc", prop2: "yutu" },
{ prop1: "xyz", prop2: "qwrq" }];
var indexes = array.reduce((a, c, i/*Current index*/) => {
if (c.prop1 == "abc") a.push(i); //Add the found index.
return a;
}, []/*Accumulator to store the found indexes.*/);
console.log(indexes);
Resource
Array.prototype.reduce()
You can use array.prototype.reduce
with shorthand if
to make it with a single line of code:
var arr = [ {prop1:"abc",prop2:"qwe"}, {prop1:"abc",prop2:"yutu"},{prop1:"xyz",prop2:"qwrq"} ];
var indexes = arr.reduce((m, e, i) => (e.prop1 === 'abc' && m.push(i), m), []);
console.log(indexes);
There is a purely functional way of doing this, but it's not particularly efficient because it requires three separate linear scans through the array:
let indexes = array.map((e, i) => [i, e])
.filter(([i, e]) => predicate(e))
.map(([i, _]) => i);
where
let predicate = e => e.prop1 === 'abc';
This works by creating a temporary array where each element is itself and array containing the original index and the element. It then filters out those where the predicate function is not true, and then strips back the arrays so that they only contain the indices.
The following code works for me:
var data = [{prop1:"abc",prop2:"qwe"},{prop1:"abc",prop2:"yutu"},{prop1:"xyz",prop2:"qwrq"}]
var indexes = []
data.forEach((element, index)=>{
if(element.prop1 =="abc"){
indexes.push(index)
}
});
console.log(indexes)
reduce
,filter
andmap
, orfor
loop best practice? Wow lots of answers in short order.. was this a dumb question? – rvictordelta Commented Feb 2, 2018 at 14:16==
when you should be using===
. – Alnitak Commented Feb 2, 2018 at 14:19