
本文介绍如何通过递归遍历 DOM,从指定容器中提取所有带 id 的嵌套元素,生成包含 ID 与子节点结构的树形数组,适用于动态菜单、可折叠组件或拖拽层级关系分析等场景。
本文介绍如何通过递归遍历 dom,从指定容器中提取所有带 `id` 的嵌套元素,生成包含 id 与子节点结构的树形数组,适用于动态菜单、可折叠组件或拖拽层级关系分析等场景。
在处理具有嵌套结构的 HTML(如可展开/折叠的树形列表、拖拽式组件容器)时,常需将 DOM 层级关系转化为结构化数据。例如,给定一个以 .child-elements-container 为根的嵌套
[
{ id: "116", children: {} },
{ id: "105", children: { id: "4", children: {} } }
]
该结构清晰表达了父子归属关系:ID "4" 是 "105" 的直接子节点,而 "116" 与 "105" 同级,均位于顶层容器下。
实现的核心在于递归遍历 + 作用域限定查询。以下为推荐方案:
如果你了解HTML,CSS和JavaScript,您已经拥有所需的工具开发Android应用程序。本动手本书展示了如何使用这些开源web标准设计和建造,可适应任何Android设备的应用程序 - 无需使用Java。您将学习如何创建一个在您选择的平台的Android友好的网络应用程序,然后转换与自由PhoneGap框架到一个原生的Android应用程序。了解为什么设备无关的移动应用是未来的潮流,并开始构建应用程序,提供更
const getChildren = (container) => {
// 查询当前容器内所有直接子 div(排除嵌套在其他非 container 元素中的 div)
const directDivs = container ? [...container.querySelectorAll(":scope > div[id]")] : [];
return directDivs.map(el => ({
id: el.id, // 提取 id 属性值(注意:id 是字符串,如 "4",非数字)
children: getChildren(el.querySelector(".child-elements-container"))
}));
};
// 从根容器开始递归
const root = document.querySelector(".child-elements-container");
const treeData = getChildren(root);
console.log(treeData);
✅ 关键说明:
- :scope > div[id] 确保只选取当前容器的直接子 中带有 id 属性的元素,避免误选深层嵌套或无关节点;
- el.querySelector(".child-elements-container") 定位每个元素下专属的子容器,作为下一层递归入口;
- 若某元素无 .child-elements-container 子节点,querySelector 返回 null,递归自动终止,children 值为 undefined —— 可根据需要统一设为 {}(如示例中所示,可在返回前加 children: getChildren(...) || {});
- id 属性值始终为字符串类型,若需数值型 ID,请显式转换:id: Number(el.id),但须确保 ID 均为有效数字(否则返回 NaN)。
⚠️ 注意事项:
- HTML 中 id 应全局唯一,且不能以数字开头(虽浏览器常容忍,但不符合规范),建议使用语义化 ID 如 item-116;
- 若存在多个同级 .child-elements-container 或非 div 类型子节点,需调整选择器逻辑;
- 大量嵌套时注意浏览器调用栈深度限制(通常 >10000 层才可能触发),实际业务中极少遇到。
此方法轻量、无依赖、兼容现代浏览器,可无缝集成至 Vue/React 组件初始化逻辑或拖拽位置计算中,为前端动态层级管理提供可靠的数据基础。
前端入门到VUE实战笔记:立即使用
在学习笔记中,你将探索 前端 的入门与实战技巧!










