如何在JavaScript中以category值为数组名分组大型对象数组
问题:按动物类别分组存储数组对象
我有一个从JSON文件转换而来的animals数组,包含19000多个对象,所有对象拥有相同的键但对应值不同,示例如下:
const animals = [ { "id": 234234, "name": "bla", "subcategory": "british short hair", "category": "cat" }, { "id": 234235, "name": "blabla", "subcategory": "bengal", "category": "cat" }, { "id": 234236, "name": "blablabla", "subcategory": "German shephard", "category": "dog" }, // 共19000+对象,涉及近90种不同category ];
我需要将同一category的对象过滤后,存入以对应category值命名的新数组。以下是我用于测试动态生成数组名的代码:
for (let i = 0; i < animals.length; i++) { if (animals[i].category === animals[i++].category){ // 以下4行仅用于测试自定义数组名称 let topLevelNaming = animals[i].category+ "__" + animals[i].categoryId; let arrName = `category_${animals[i].category}`; // console.log(topLevelNaming); let nameString = `${animals[i].category}__${animals[i].techName}`; console.log(nameString); }}
解决方案
推荐方案:使用对象统一管理分组数组(最佳实践)
这种方式不会污染全局作用域,且便于统一维护所有分组结果:
// 初始化一个空对象,用于存储所有分组后的数组 const groupedAnimals = {}; // 遍历animals数组 for (const animal of animals) { const category = animal.category; // 如果当前类别还未创建数组,先初始化空数组 if (!groupedAnimals[category]) { groupedAnimals[category] = []; } // 将当前动物对象加入对应类别的数组 groupedAnimals[category].push(animal); }
使用方式:
- 获取所有猫的数组:
groupedAnimals.cat - 获取所有狗的数组:
groupedAnimals.dog - 以此类推,所有类别都可以通过
groupedAnimals[类别名称]访问
不推荐方案:动态生成全局变量
如果一定要生成独立的全局数组变量(不建议,易造成变量冲突),可以在浏览器环境通过window对象实现:
for (const animal of animals) { const category = animal.category; // 动态创建全局数组变量 if (!window[category]) { window[category] = []; } window[category].push(animal); }
使用方式:直接通过cat、dog等变量访问对应数组。
测试代码的问题说明
你之前的测试代码存在逻辑错误:animals[i++]会让循环的i在单次循环中自增两次(一次是for循环的i++,一次是if判断里的i++),导致大量元素被跳过,无法正确遍历整个数组。
内容的提问来源于stack exchange,提问作者HaYaDa
相关产品推荐
相关产品推荐

