如何将周/日对象数组转为结构化对象?reduce方法报错排查
问题:按周分组对象数组的reduce实现错误修正
我有一个如下格式的对象数组:
const program = [ { id: '1', week: 1, day: 1, description: 'week 1 day 1', completed: true }, { id: '2', week: 1, day: 2, description: 'week 1 day 2', completed: true }, { id: '3', week: 1, day: 3, description: 'week 1, day 3', completed: true }, { id: '4', week: 2, day: 1, description: 'week 2, day 1', completed: true }, { id: '5', week: 2, day: 2, description: 'week 2 day 2', completed: false }, { id: '6', week: 2, day: 3, description: 'week 2 day 3', completed: true }, { id: '7', week: 3, day: 1, description: 'week 3, day 1', completed: false }, // .... { id: '89', week: 11, day: 9, description: 'week 11, day 9', completed: false }, // ... ];
期望得到按周分组的结构化对象输出:
const weekMap = { 1: [ { id: '1', week: 1, day: 1, description: 'week 1 day 1', completed: true }, { id: '2', week: 1, day: 2, description: 'week 1 day 2', completed: true }, { id: '3', week: 1, day: 3, description: 'week 1, day 3', completed: true }, ], 2: [ { id: '4', week: 2, day: 1, description: 'week 2, day 1', completed: true }, { id: '5', week: 2, day: 2, description: 'week 2 day 2', completed: false }, { id: '6', week: 2, day: 3, description: 'week 2 day 3', completed: true }, ], 3: [ { id: '7', week: 3, day: 1, description: 'week 3, day 1', completed: false }, // .... ], 11: [ { id: '89', week: 11, day: 9, description: 'week 11, day 9', completed: false }, // .... ], };
尝试用reduce方法实现时出现报错,代码如下:
export const toWeekMap = (programSteps) => programSteps.reduce((acc, curr) => { if (!acc[curr.week]) { acc[curr.week] = []; } if (!acc[curr.week][curr.day]) { acc[curr.week][curr.day] = []; } console.log(acc); return acc[curr.week][curr.day].push(curr); }, {});
错误信息:
Uncaught TypeError: Cannot create property '1' on number '1'
错误原因分析
- reduce返回值错误:
Array.push()方法返回的是数组的新长度(数字类型),你在每次迭代最后返回了这个数值,导致下一次迭代时acc不再是初始的空对象,而是变成了数字。数字无法添加属性,因此后续访问acc[curr.week]时抛出错误。 - 多余的按天分组逻辑:你的需求是按周分组,每个周对应的是包含所有该周天数项的数组,但代码里额外添加了按
day再分组的逻辑(把每个周的数组又拆成了按day为key的子数组),这和目标结构不符。
修正后的代码
export const toWeekMap = (programSteps) => programSteps.reduce((acc, curr) => { // 如果当前周的数组不存在,初始化一个空数组 if (!acc[curr.week]) { acc[curr.week] = []; } // 将当前项push到对应周的数组中 acc[curr.week].push(curr); // 必须返回累计器acc,保证下一次迭代能继续使用这个对象 return acc; }, {});
内容的提问来源于stack exchange,提问作者nyphur
相关产品推荐
相关产品推荐

