
本文详解如何在 react 中正确使用双重 `.map()` 渲染嵌套数据结构(如课程列表及其子科目),避免常见错误(如误将数组当对象访问),并提供可直接运行的代码示例与最佳实践。
在 React 中,当数据呈层级结构(例如每个课程对象包含一个 subjects 数组)时,仅用单层 .map() 无法展开子项——这是初学者常遇到的典型问题。原代码中 course.subjects.class 报错,正是因为 subjects 是数组而非对象,不能直接点取 class 属性。
正确的做法是:外层 .map() 遍历 courses 数组生成课程区块;内层 .map() 遍历每个 course.subjects 数组生成科目列表项。同时需严格遵守 React 列表渲染规范:为每一级动态元素提供唯一且稳定的 key,并确保语义化 HTML 结构(如用 <ul> 包裹 <li>)。
以下是修正后的完整实现:
export const courses = [
{
id: 0,
title: "first year",
subjects: [
{ id: 0, class: "french" },
{ id: 1, class: "history" },
{ id: 2, class: "geometry" }
],
},
{
id: 1,
title: "second year",
subjects: [
{ id: 0, class: "geography" },
{ id: 1, class: "chemistry" }
],
}
];
// ✅ 正确:嵌套 map + 合理 key + 语义化标签
export const studies = courses.map((course) => (
<div key={course.id}>
<h2>{course.title}</h2>
<ul>
{course.subjects.map((subject) => (
<li key={subject.id}>{subject.class}</li>
))}
</ul>
</div>
));关键注意事项:
- ? key 必须放在直接由 .map() 返回的 JSX 元素上(即 <div> 和 <li>),不可放在其子元素或 Fragment 中;
- ? subjects 是数组,必须用 .map()、.forEach() 等数组方法遍历,不可当作对象解构(如 course.subjects.class 会返回 undefined);
- ⚠️ 若 subjects 可能为空或未定义,建议添加防护性检查:{course.subjects?.length > 0 && (...)} 或 Array.isArray(course.subjects) && course.subjects.map(...);
- ? 如需进一步交互(如点击科目跳转),可在内层 map 中绑定事件处理器,但注意避免在循环中创建新函数(推荐提取为具名函数或使用 useCallback 优化)。
通过这种嵌套映射模式,你不仅能清晰呈现多级数据,还能保持组件的可维护性与性能——这是构建课程管理、商品分类、组织架构等层级 UI 的基础范式。










