simple example, want to return an array of arrays. For each name in 'peeps' I want to push an array with the word 'hello' into the accumulator.
const peeps = ['sally', 'nick', 'dave'];
return peeps.reduce((acc, val) => {
return acc.push(['hello'])
}, []);
It keeps saying that acc.push() is not a function.
Can someone please help me understand why this does not work.
simple example, want to return an array of arrays. For each name in 'peeps' I want to push an array with the word 'hello' into the accumulator.
const peeps = ['sally', 'nick', 'dave'];
return peeps.reduce((acc, val) => {
return acc.push(['hello'])
}, []);
It keeps saying that acc.push() is not a function.
Can someone please help me understand why this does not work.
Share Improve this question edited Jan 27, 2017 at 10:08 Josh Pittman asked Jan 27, 2017 at 9:23 Josh PittmanJosh Pittman 7,3248 gold badges43 silver badges67 bronze badges 3 |4 Answers
Reset to default 18You use Array#push
The
push()
method adds one or more elements to the end of an array and returns the new length of the array.
this returns the length of the array after pushing. Then the accumulator value is a number, not an array
return acc.push(['hello']) // 1
Solution 1: Return the array instead of the result of pushing.
const peeps = ['sally', 'nick', 'dave'];
console.log(peeps.reduce((acc, val) => {
acc.push(['hello']);
return acc;
}, []));
Solution 2: Use Array#concat
.
The
concat()
method is used to merge two or more arrays. This method does not change the existing arrays, but instead returns a new array.
I would avoid using it with large amounts of data though, as it is a lot less efficient than push. jsPerf
const peeps = ['sally', 'nick', 'dave'];
console.log(peeps.reduce((acc, val) => acc.concat([['hello']]), []));
Solution 3: Use Array#map
. This works best, if the result array should have the same length as the given array.
The
map()
method creates a new array with the results of calling a provided function on every element in this array.
const peeps = ['sally', 'nick', 'dave'];
console.log(peeps.map(val => ['hello']));
Try this instead:
const peeps = ['sally', 'nick', 'dave'];
return peeps.reduce((acc, val) => {
acc.push(['hello']);
return acc;
}, []);
push
does not return acc, you have to do it manually.
I think you should try map. Instead of reduce.
const peeps = ['sally', 'nick', 'dave'];
return peeps.map((val) => {
return ['hello']
});
It will return an array [ ['Hello'],['Hello'],['Hello'] ]
Reduce is used to get a single value from an array. For example a count, sum, product and so on.
@Nina's answer is precise and correct.
In addition, recent versions (ES2015 or ES6 and later) of JavaScript supports spread operator syntax that allows you to conveniently return a copy of an array:
const peeps = ["sally", "nick", "dave"];
const output1 = peeps.reduce((acc, _val) => [...acc, "hello"], []); // [ 'hello', 'hello', 'hello' ]
const output2 = peeps.reduce(
(acc, val) => [...acc, `"hello" from ${val}`],
[]
); // [ '"hello" from sally', '"hello" from nick', '"hello" from dave' ]
That's the preferred way of going about these things these days.
return acc.concat(['hello']);
. – user663031 Commented Jan 27, 2017 at 9:28