您的位置:首页 > 房产 > 建筑 > 中央下令全国解封通知_河南国邦卫可生物科技有限公司网站建设_百度云网盘资源分享网站_宁波seo快速排名

中央下令全国解封通知_河南国邦卫可生物科技有限公司网站建设_百度云网盘资源分享网站_宁波seo快速排名

2025/4/20 23:39:17 来源:https://blog.csdn.net/weixin_46094786/article/details/147306873  浏览:    关键词:中央下令全国解封通知_河南国邦卫可生物科技有限公司网站建设_百度云网盘资源分享网站_宁波seo快速排名
中央下令全国解封通知_河南国邦卫可生物科技有限公司网站建设_百度云网盘资源分享网站_宁波seo快速排名

使用 `requestIdleCallback` 优化大批量 DOM 操作 —— 以加载 100 万条数据为例

在前端开发中,如果你尝试在短时间内往 DOM 中添加大量元素,比如一次性插入 100 万条数据,页面极有可能卡顿甚至直接崩溃。为了解决这一性能问题,我们可以借助浏览器提供的 `requestIdleCallback` 方法,利用浏览器空闲时间进行渐进式渲染。

本文将介绍 `requestIdleCallback` 的原理,并通过一个加载百万数据的例子,展示如何优化加载逻辑。我们会进行优化前后的代码对比,并最终输出完整的优化后代码。


🧠 `requestIdleCallback` 是什么?

`requestIdleCallback` 是浏览器提供的一种任务调度 API,它允许我们在主线程空闲时执行低优先级任务,从而避免阻塞用户交互。

基本用法:

requestIdleCallback(callback, { timeout });
  • `callback(deadline)`:将在浏览器空闲时执行的回调函数。
  • `deadline.timeRemaining()`:表示当前空闲周期内的剩余可用毫秒数。
  • `timeout`(可选):指定在多少毫秒内必须执行任务,即使浏览器一直不空闲。

📌 应用场景:

  • 批量数据渲染
  • 懒加载组件
  • 异步加载脚本
  • 用户不感知的任务(如埋点、缓存处理等)

📉 性能问题分析(未优化)

假设我们要一次性渲染 100 万条数据,最直观的做法就是通过 `for` 循环和 DOM 操作一次性插入:

开始渲染

function startRender() {for (let i = 0; i < 1000000; i++) {const div = document.createElement('div');div.textContent = \`第\${i + 1}条数据\`;document.body.appendChild(div);}
}

⚠️ 问题:

  • 页面会严重卡顿,甚至浏览器崩溃。
  • 用户在等待过程中无法滚动、点击或交互。
  • 非渐进式渲染,缺乏灵活性。

✅ 使用 `requestIdleCallback` 优化后的方案

我们将渲染任务分批处理,并在每次主线程空闲时执行下一批操作。这样浏览器可以在用户交互和渲染之间进行调度,避免“线程阻塞”。

优化思路:

  • 每批最多渲染 100 条数据。
  • 使用 `document.createDocumentFragment` 减少 DOM 操作开销。
  • 使用 `requestIdleCallback` 判断是否还有空闲时间继续渲染。

🔍 优化前后对比图示(伪图)

未优化:一次性插入100w条
┌────┬────┬────┬────┬────┬────┐
│████████████ 卡顿 ███████████│
└────┴────┴────┴────┴────┴────┘

优化后:空闲时分批插入100条
┌█───█───█───█───█───█───█───█┐
│ 渐进渲染中… 用户可交互 │
└█───█───█───█───█───█───█───█┘


🧪 完整优化后代码示例

100W条数据加载-优化版 开始智能加载
<script>const TOTAL_ITEMS = 1000000;let loadedCount = 0;// 创建文档片段优化DOM操作function createBatch() {const fragment = document.createDocumentFragment();const batchSize = Math.min(100, TOTAL_ITEMS - loadedCount);for(let i=0; i<batchSize; i++) {const div = document.createElement('div');div.textContent = \`第\${++loadedCount}条数据\`;fragment.appendChild(div);}document.body.appendChild(fragment);return loadedCount < TOTAL_ITEMS;}// 使用requestIdleCallback调度function scheduleLoading() {requestIdleCallback((deadline) => {const startTime = performance.now();let hasMore = true;while (deadline.timeRemaining() > 0 && hasMore &&performance.now() - startTime < 50 // 防止单次执行过久) {hasMore = createBatch();}if(hasMore) {scheduleLoading();} else {console.log('所有数据加载完成');}}, { timeout: 1000 });}function startLoading() {loadedCount = 0;scheduleLoading();}
</script>

📌 总结

  • `requestIdleCallback` 提供了一种非常适合执行非关键任务的机制。
  • 对于大批量 DOM 操作,我们应避免一次性操作 DOM,采用分批 + 空闲加载策略。
  • 在用户体验和页面性能之间找到平衡,是现代前端优化的核心。

✨ 如果你觉得这篇文章对你有帮助,不妨点个 免费的赞 或留言交流哦!

版权声明:

本网仅为发布的内容提供存储空间,不对发表、转载的内容提供任何形式的保证。凡本网注明“来源:XXX网络”的作品,均转载自其它媒体,著作权归作者所有,商业转载请联系作者获得授权,非商业转载请注明出处。

我们尊重并感谢每一位作者,均已注明文章来源和作者。如因作品内容、版权或其它问题,请及时与我们联系,联系邮箱:809451989@qq.com,投稿邮箱:809451989@qq.com