介绍
Reduce是一种难以理解的方法,尤其是在网络上可以找到所有含糊不清的解释的情况下。理解reduce
它有很多好处,因为它经常用于状态管理(想想Redux)。
reduce
JavaScript 中数组方法的签名是:
arr.reduce(callback, initialValue);
术语
Reduce 带有一些术语,例如reducer 和 accumulator。这accumulator
是我们结束的值,reducer
也是我们将执行的操作以获得一个值。
您必须记住,reducer只会返回一个值和一个值,因此名称为reduce。
以下面的经典例子为例:
const value = 0;
const numbers = [5, 10, 15];
for(let i = 0; i < numbers.length; i++) {
value += numbers[i];
}
以上将给我们30
(5 + 10 + 15)。这工作得很好,但我们可以用它reduce
来代替,这将使我们免于改变我们的value
变量。
下面的代码也将输出30
,但不会改变我们的value
变量(我们现在称之为initialValue
)
/* this is our initial value i.e. the starting point*/
const initialValue = 0;
/* numbers array */
const numbers = [5, 10, 15];
/* reducer method that takes in the accumulator and next item */
const reducer = (accumulator, item) => {
return accumulator + item;
};
/* we give the reduce method our reducer function
and our initial value */
const total = numbers.reduce(reducer, initialValue)
上面的代码可能看起来有点混乱,但在引擎盖下并没有什么神奇之处。让我们console.log
在我们的reducer
方法中添加一个将输出accumulator
和item
参数。
以下屏幕截图显示了记录到控制台的内容:
所以我们注意到的第一件事是我们的方法被调用了3
多次,因为3
我们的数组中有值。我们累加器始于0
这是我们的initialValue
,我们传递给reduce
。每次调用该函数时,item
都会添加到accumulator
. 对该方法的最终调用具有和is的accumulator
值,给出了我们的最终值。请记住该方法返回加号。15
item
15
15 + 15
30
reducer
accumulator
item
这是一个关于如何使用 的简单示例reduce
,现在让我们深入研究一个更复杂的示例。
使用 Reduce 展平数组
假设我们有以下数组:
const numArray = [1, 2, [3, 10, [11, 12]], [1, 2, [3, 4]], 5, 6];
假设出于某种疯狂的原因,JavaScript 删除了该.flat
方法,因此我们必须自己展平这个数组。
因此,无论数组嵌套多深,我们都将编写一个函数来展平任何数组:
function flattenArray(data) {
// our initial value this time is a blank array
const initialValue = [];
// call reduce on our data
return data.reduce((total, value) => {
// if the value is an array then recursively call reduce
// if the value is not an array then just concat our value
return total.concat(Array.isArray(value) ? flattenArray(value) : value);
}, initialValue);
}
如果我们将我们的传递numArray
给这个方法并记录结果,我们会得到以下结果:
这是一个很好的例子,说明我们如何使非常常见的操作变得非常简单。
让我们再看一个例子。
最后一个示例 – 更改对象结构
因此,随着新的 Pokemon 游戏的出现,让我们假设我们有一个服务器向我们发送 Pokemon 对象数组,如下所示:
const pokemon = [
{ name: "charmander", type: "fire" },
{ name: "squirtle", type: "water" },
{ name: "bulbasaur", type: "grass" }
]
我们想把这个对象改成这样:
const pokemonModified = {
charmander: { type: "fire" },
squirtle: { type: "water" },
bulbasaur: { type: "grass" }
};
为了获得所需的输出,我们执行以下操作:
const getMapFromArray = data =>
data.reduce((acc, item) => {
// add object key to our object i.e. charmander: { type: 'water' }
acc[item.name] = { type: item.type };
return acc;
}, {});
如果我们像这样调用我们的方法:
getMapFromArray(pokemon)
我们得到了我们想要的输出:
您可以在此处查看Codesandbox。
结论
乍一看,它reduce
比其他JavaScript 数组迭代方法(如map
和 )看起来更复杂filter
,但是一旦理解了语法、核心概念和用例,它就可以成为 JavaScript 开发人员的另一个强大工具。