NodeJS按指定数组项分组另一数组,需保留无匹配空分组
解决按指定数组分组并保留空类别问题
我完全懂你的需求——要按照dataCms里的每一项对outJSON进行分组,而且哪怕某个类别没有匹配的数据,也得保留它对应的空数组。之前的代码之所以会丢失空分组,大概率是直接从outJSON里提取cms值来创建分组键,这样没出现过的自然就被漏掉了。下面给你两种简单靠谱的解决方法:
方法一:先初始化所有分组,再填充数据
这种思路最直观:先把dataCms里的每个类别都初始化为空数组,确保所有键都存在,再遍历数据填充对应分组。
var dataCms = ["BIG BIKE","CUB","MATIC","SPORT"]; var outJSON = [ {"id": "42513b49-9bd8-11e9-a417-560001ead144", "series": "GENIO", "cms": "MATIC"}, {"id": "5d8ae0f0-cda0-4c1d-be01-1bfd422a3cf4", "series": "VARIO", "cms": "MATIC"}, {"id": "5d8ae0f0-cda0-4c1d-be01-1bfd422a3cf4", "series": "BEAT", "cms": "MATIC"}, {"id": "5d8ae0f0-cda0-4c1d-be01-1bfd422a3cf4", "series": "SUPRA", "cms": "CUB"}, {"id": "5d8ae0f0-cda0-4c1d-be01-1bfd422a3cf4", "series": "SONIC", "cms": "SPORT"}, {"id": "5d8ae0f0-cda0-4c1d-be01-1bfd422a3cf4", "series": "REVO", "cms": "CUB"}, {"id": "5d8ae0f0-cda0-4c1d-be01-1bfd422a8900", "series": "GENIO", "cms": "MATIC"} ]; // 第一步:初始化所有分组为空数组 const groupedResult = dataCms.reduce((acc, cmsType) => { acc[cmsType] = []; return acc; }, {}); // 第二步:遍历outJSON,把数据填充到对应分组 outJSON.forEach(item => { // 只处理dataCms里有的类别(防止outJSON里出现未知cms值) if (groupedResult.hasOwnProperty(item.cms)) { groupedResult[item.cms].push(item); } }); console.log(groupedResult);
运行后你会得到这样的结果:
{ "BIG BIKE": [], "CUB": [{"id": "5d8ae0f0-cda0-4c1d-be01-1bfd422a3cf4", "series": "SUPRA", "cms": "CUB"}, {"id": "5d8ae0f0-cda0-4c1d-be01-1bfd422a3cf4", "series": "REVO", "cms": "CUB"}], "MATIC": [{"id": "42513b49-9bd8-11e9-a417-560001ead144", "series": "GENIO", "cms": "MATIC"}, {"id": "5d8ae0f0-cda0-4c1d-be01-1bfd422a3cf4", "series": "VARIO", "cms": "MATIC"}, {"id": "5d8ae0f0-cda0-4c1d-be01-1bfd422a3cf4", "series": "BEAT", "cms": "MATIC"}, {"id": "5d8ae0f0-cda0-4c1d-be01-1bfd422a8900", "series": "GENIO", "cms": "MATIC"}], "SPORT": [{"id": "5d8ae0f0-cda0-4c1d-be01-1bfd422a3cf4", "series": "SONIC", "cms": "SPORT"}] }
方法二:使用Map来管理分组
如果你更习惯用Map(尤其适合需要保持键顺序的场景),可以用这种方式:
// 用dataCms初始化Map,每个键对应空数组 const groupMap = new Map(dataCms.map(cms => [cms, []])); // 填充数据 outJSON.forEach(item => { if (groupMap.has(item.cms)) { groupMap.get(item.cms).push(item); } }); // 若需要转为普通对象,用Object.fromEntries const groupedResult = Object.fromEntries(groupMap); console.log(groupedResult);
这个方法的结果和方法一完全一致,而且Map天然会保留dataCms的原始顺序,如果你需要顺序严格和原数组一致的话,这个方式更省心。
核心思路总结
不管用哪种方法,关键都是先确保所有需要的分组键都存在并初始化为空数组,再去填充匹配的数据。这样就不会漏掉任何dataCms里的项啦~
内容的提问来源于stack exchange,提问作者Ratri
相关产品推荐
相关产品推荐

