对象按分类值分组并生成带变体数组的方法
时间:2026-06-25 07:01
使用reduce按分类字段分组,通过Object keys() map()转换结构,取每组首个对象为主项,变体字段依据对象数量设为数组或null。整体时间复杂度O(n),适用于商品管理、内容聚合等场景。
在日常前端开发中,我们经常需要处理一类常见需求:手头有一组扁平化数据,例如商品列表,希望按照品类进行聚合——将同一品类的所有商品挂载到该品类第一个出现的商品之下,形成“主商品 + 变体”的层级结构。如果某个品类只有一件商品,则将其变体字段设为 `null`。这看似只是一个数据透视的小任务,但实现时,选择合适的方法能显著提升效率。
接下来,本文将分享一套经过实践验证的两阶段处理方案,兼顾执行性能与代码可读性,适用于商品管理、内容聚合、配置分组等多种业务场景。
---
### 第一步:分组聚合——使用 `reduce` 构建哈希映射
以目标字段(例如 `category`)作为键,遍历原始数组,将相同分类的对象收集到同一个数组内。这一步的时间复杂度为 O(n),且代码非常直观:
```ja vascript
const grouped = products.reduce((acc, product) => {
const { category } = product;
if (!acc[category]) acc[category] = [];
acc[category].push(product);
return acc;
}, {});
```
### 第二步:结构转换——通过 `Object.keys().map()` 生成最终结果
获得分组结果后,遍历每一个分类键,提取该分类中第一个对象的 `position` 和 `category` 作为主项信息,再根据该分类的总对象数量决定 `variants` 的值——若多于一个,则将整个数组放入;否则设为 `null`。
```ja vascript
const result = Object.keys(grouped).map(key => {
const items = grouped[key];
return {
position: items[0].position,
category: key,
variants: items.length > 1 ? items : null
};
});
```
用一个实际示例验证,结果正如预期:
```ja vascript
const products = [
{ position: 1, category: "jeans" },
{ position: 2, category: "tees" },
{ position: 3, category: "dress" },
{ position: 4, category: "dress" },
{ position: 5, category: "dress" },
];
// 输出:
// [
// { position: 1, category: "jeans", variants: null },
// { position: 2, category: "tees", variants: null },
// { position: 3, category: "dress", variants: [ { position:3, category:"dress" }, { position:4, category:"dress" }, { position:5, category:"dress" } ] }
// ]
```
---
### ? 关键注意事项
- **分组字段灵活扩展**:若业务需要按多个字段联合分组(例如 `category` + `brand`),只需将哈希表的键改为 `"${category}-${brand}"`,其余逻辑无需调整。
- **首项 position 仅作示例**:上述代码取得第一个对象的 `position`,如果实际需求是取最小或最大值,可替换为 `Math.min(...items.map(p => p.position))` 或 `Math.max(...)`,灵活适配。
- **空数组安全处理**:若原始数组为空,`Object.keys(grouped).map(...)` 将直接返回空数组 `[]`,无需额外判空。
- **`variants: null` 的设计优势**:这种输出结构在模板渲染中非常便利,例如在 Vue/React 中通过 `v-if="item.variants"` 即可控制变体区域的显示与隐藏。
该模式的核心优势在于:仅需单次遍历 + 哈希查找,整体时间复杂度为 O(n);代码结构清晰,边界情况处理完善。无论是商品列表的归类展示,还是配置选项的合并,都可以直接套用。下次遇到扁平数据需要“按组分构建变体”的场景时,不妨将其作为标准解法记录下来。
来源:https://www.php.cn/faq/2696132.html
本站内容用于信息整理与展示,如有侵权或内容问题请及时联系处理。