Map.groupBy()

Limited availability

This feature is not Baseline because it does not work in some of the most widely-used browsers.

注意:在某些浏览器的某些版本中,该方法被实现为方法 Array.prototype.groupToMap()。由于网络兼容性问题,它现在以静态方法实现。检查 浏览器兼容性表 了解详细信息。

¥Note: In some versions of some browsers, this method was implemented as the method Array.prototype.groupToMap(). Due to web compatibility issues, it is now implemented as a static method. Check the browser compatibility table for details.

Map.groupBy() 静态方法使用提供的回调函数返回的值对给定可迭代的元素进行分组。最终返回的 Map 使用测试函数中的唯一值作为键,可用于获取每个组中的元素数组。

¥The Map.groupBy() static method groups the elements of a given iterable using the values returned by a provided callback function. The final returned Map uses the unique values from the test function as keys, which can be used to get the array of elements in each group.

该方法主要在对与对象关联的元素进行分组时有用,特别是当该对象可能随时间变化时。如果对象是不变的,你可以使用字符串来表示它,并使用 Object.groupBy() 对元素进行分组。

¥The method is primarily useful when grouping elements that are associated with an object, and in particular when that object might change over time. If the object is invariant, you might instead represent it using a string, and group elements with Object.groupBy().

Try it

语法

¥Syntax

js
Map.groupBy(items, callbackFn)

参数

¥Parameters

items

一个 iterable(例如 Array),其元素将被分组。

callbackFn

为迭代中的每个元素执行的函数。它应该返回一个值(objectprimitive),指示当前元素的组。使用以下参数调用该函数:

element

当前正在处理的元素。

index

当前正在处理的元素的索引。

返回值

¥Return value

一个 Map 对象,每个组都有键,每个键都分配给一个包含关联组元素的数组。

¥A Map object with keys for each group, each assigned to an array containing the elements of the associated group.

描述

¥Description

Map.groupBy() 为可迭代中的每个元素调用一次提供的 callbackFn 函数。回调函数应返回一个值,指示关联元素的组。callbackFn 返回的值用作 Map.groupBy() 返回的 Map 的键。每个键都有一个关联的数组,其中包含回调返回相同值的所有元素。

¥Map.groupBy() calls a provided callbackFn function once for each element in an iterable. The callback function should return a value indicating the group of the associated element. The values returned by callbackFn are used as keys for the Map returned by Map.groupBy(). Each key has an associated array containing all the elements for which the callback returned the same value.

返回的 Map 和原始可迭代中的元素相同(不是 deep copies)。更改元素的内部结构将反映在原始可迭代对象和返回的 Map 中。

¥The elements in the returned Map and the original iterable are the same (not deep copies). Changing the internal structure of the elements will be reflected in both the original iterable and the returned Map.

当你需要对与可能随时间变化的特定对象相关的信息进行分组时,此方法非常有用。这是因为即使该对象被修改,它仍将继续作为返回的 Map 的键。如果你为对象创建字符串表示形式并将其用作 Object.groupBy() 中的分组键,则必须在对象更改时维护原始对象与其表示形式之间的映射。

¥This method is useful when you need to group information that is related to a particular object that might potentially change over time. This is because even if the object is modified, it will continue to work as a key to the returned Map. If you instead create a string representation for the object and use that as a grouping key in Object.groupBy(), you must maintain the mapping between the original object and its representation as the object changes.

注意:要访问返回的 Map 中的组,你必须使用最初用作 Map 中的键的同一对象(尽管你可以修改其属性)。你不能使用恰好具有相同名称和属性的另一个对象。

¥Note: To access the groups in the returned Map, you must use the same object that was originally used as a key in the Map (although you may modify its properties). You can't use another object that just happens to have the same name and properties.

Map.groupBy 不读取 this 的值。可以在任何对象上调用它,并且将返回一个新的 Map 实例。

¥Map.groupBy does not read the value of this. It can be called on any object and a new Map instance will be returned.

示例

¥Examples

使用 Map.groupBy()

¥Using Map.groupBy()

首先,我们定义一个包含代表不同食品库存的对象的数组。每种食物都有一个 type 和一个 quantity

¥First we define an array containing objects representing an inventory of different foodstuffs. Each food has a type and a quantity.

js
const inventory = [
  { name: "asparagus", type: "vegetables", quantity: 9 },
  { name: "bananas", type: "fruit", quantity: 5 },
  { name: "goat", type: "meat", quantity: 23 },
  { name: "cherries", type: "fruit", quantity: 12 },
  { name: "fish", type: "meat", quantity: 22 },
];

下面的代码使用 Map.groupBy() 和箭头函数,该函数返回名为 restocksufficient 的对象键,具体取决于元素是否具有 quantity < 6。返回的 result 对象是 Map,因此我们需要使用 key 调用 get() 来获取数组。

¥The code below uses Map.groupBy() with an arrow function that returns the object keys named restock or sufficient, depending on whether the element has quantity < 6. The returned result object is a Map so we need to call get() with the key to obtain the array.

js
const restock = { restock: true };
const sufficient = { restock: false };
const result = Map.groupBy(inventory, ({ quantity }) =>
  quantity < 6 ? restock : sufficient,
);
console.log(result.get(restock));
// [{ name: "bananas", type: "fruit", quantity: 5 }]

请注意,函数参数 { quantity }函数参数的对象解构语法 的基本示例。这将解压作为参数传递的对象的 quantity 属性,并将其分配给函数体中名为 quantity 的变量。这是一种访问函数内元素相关值的非常简洁的方法。

¥Note that the function argument { quantity } is a basic example of object destructuring syntax for function arguments. This unpacks the quantity property of an object passed as a parameter, and assigns it to a variable named quantity in the body of the function. This is a very succinct way to access the relevant values of elements within a function.

Map 的密钥可以修改并仍然使用。但是,你无法重新创建密钥并仍然使用它。因此,任何需要使用映射的东西都必须保留对其键的引用,这一点很重要。

¥The key to a Map can be modified and still used. However you can't recreate the key and still use it. For this reason it is important that anything that needs to use the map keeps a reference to its keys.

js
// The key can be modified and still used
restock["fast"] = true;
console.log(result.get(restock));
// [{ name: "bananas", type: "fruit", quantity: 5 }]

// A new key can't be used, even if it has the same structure!
const restock2 = { restock: true };
console.log(result.get(restock2)); // undefined

规范

Specification
Array Grouping
# sec-map.groupby

¥Specifications

浏览器兼容性

BCD tables only load in the browser

¥Browser compatibility

也可以看看