documentfragment能减少重排,因其是离线容器,所有操作在内存中进行,不触发布局计算;仅最后一次性插入真实dom时才引发一次重排。

用 DocumentFragment 批量插入元素,核心是把多个 DOM 操作“攒起来”,只触发一次真实插入,从而避免反复重排。它本身不挂载到页面,只是个轻量容器,最后一次性 append 到目标节点,浏览器只需计算一次布局。
为什么 DocumentFragment 能减少重排
每次向真实 DOM(比如 body 或某个 div)直接 appendChild 一个新元素,如果该元素已渲染、有样式或影响布局,浏览器可能立即触发重排(Reflow)。连续插入 10 个节点,就可能触发 10 次重排(尤其在旧引擎或复杂样式下)。DocumentFragment 是离线节点,所有操作都在内存中完成,不触发任何布局计算;只有最后调用 parent.appendChild(fragment) 时,才把整个片段“整体”插入,只引起一次重排(甚至可能被优化为一次重绘)。
基本用法:创建 → 填充 → 一次性插入
以动态生成 100 个列表项为例:
const fragment = document.createDocumentFragment();
const ul = document.getElementById('myList');
for (let i = 0; i
结合模板字符串或 innerHTML 的注意事项
DocumentFragment 不能直接设置 innerHTML,但可以绕过:
- 先用
div临时解析 HTML 字符串:const temp = document.createElement('div'); temp.innerHTML = htmlString; - 再把
temp.content(如果是template元素)或temp.children移入 fragment - 更推荐方式:用
template元素 +content.cloneNode(true),再 append 到 fragment
现代替代方案与适用场景
虽然 DocumentFragment 依然有效,但要注意:
- 现代浏览器对小批量插入(如几十个节点)做了很多优化,重排压力比过去小
- 若使用 React/Vue 等框架,它们的虚拟 DOM 已自动批处理,无需手动干预
- 真正高频、大量、无框架的 DOM 构建(如表格渲染、无限滚动加载)仍推荐
DocumentFragment - 也可配合
requestIdleCallback或分片(chunking)进一步防阻塞主线程











