当前位置: 首页 > news >正文

网站公众号建设工具中国建筑集团有限公司有几个局

网站公众号建设工具,中国建筑集团有限公司有几个局,网页简单模板下载,微信小程序个人可以做吗面试官:同时插入100000个元素怎么让页面不卡顿 优化前写法 首先我们来看下面的一段,点击按钮后,循环100000次,每次都插入一个元素,并且插入区域上方还有一个小球在滚动,在插入的过程中我们可以观察小球的…

面试官:同时插入100000个元素怎么让页面不卡顿

优化前写法

首先我们来看下面的一段,点击按钮后,循环100000次,每次都插入一个元素,并且插入区域上方还有一个小球在滚动,在插入的过程中我们可以观察小球的动画是否出现卡顿

<template><h3>小球左右上下循环移动动画</h3><div class="container"><div id="ball" class="ball"></div></div><h3>前端性能优化之</h3><el-button type="primary" @click='addBall'>加载10000个小球</el-button><div id='ballBox' class='ballBox'></div>
</template><script setup>onMounted(() => {const ball = document.getElementById('ball')const container = document.querySelector('.container')// 获取容器的宽高const containerWidth = container.offsetWidthconst containerHeight = container.offsetHeight// 小球的初始位置和速度let ballX = 0let ballY = 0let speedX = 2 // 水平速度let speedY = 2 // 垂直速度// 动画函数function moveBall() {// 更新小球的位置ballX += speedXballY += speedY// 检测边界碰撞并反转方向if (ballX <= 0 || ballX + ball.offsetWidth >= containerWidth) {speedX = -speedX}if (ballY <= 0 || ballY + ball.offsetHeight >= containerHeight) {speedY = -speedY}// 应用新的位置ball.style.left = `${ballX}px`ball.style.top = `${ballY}px`// 循环调用动画requestAnimationFrame(moveBall)}// 启动动画moveBall()
})function addBall(){let ballBox = document.getElementById('ballBox')const tasks = Array.from({ length: 100000 }, (_, i) => {return () => {let ball = document.createElement('div')ball.innerText = i + 1ballBox.appendChild(ball)}})for (let i = 0; i < tasks.length; i++) {tasks[i]()}
}
</script><style scoped>
.container {position: relative;width: 400px;height: 300px;border: 2px solid #ccc;background-color: #f5f5f5;overflow: hidden; /* 防止小球超出容器 */
}.ball {position: absolute;width: 30px;height: 30px;background-color: red;border-radius: 50%; /* 圆形 */
}
</style>

目前的效果

gifimg2

可以看到点击后小球明显的出现了一段时间的卡顿才恢复正常

使用DocumentFragment减少DOM操作

DocumentFragment 是一个轻量级的文档对象,可以作为一个临时的容器来存储一组节点。它的主要优点是可以减少对 DOM 的多次操作,从而提高性能。我们可以将多个节点添加到 DocumentFragment 中,然后一次性将 DocumentFragment 添加到 DOM 中。从而较少浏览器的重绘和回流

改写代码如下

function addBall() {// 获取要添加小球的容器元素let ballBox = document.getElementById('ballBox')// 创建一个 DocumentFragment,用于批量添加小球const fragment = document.createDocumentFragment()// 创建一个包含 100000 个任务的数组,每个任务用于创建一个小球并添加到 fragment 中const tasks = Array.from({ length: 100000 }, (_, i) => {return () => {// 创建一个 div 元素表示小球let ball = document.createElement('div')// 设置小球的文本内容为其序号ball.innerText = i + 1// 将小球添加到 fragment 中fragment.appendChild(ball)}})// 执行所有任务,将小球添加到 fragment 中for (let i = 0; i < tasks.length; i++) {tasks[i]()}// 将 fragment 添加到 ballBox 中ballBox.appendChild(fragment)
}

但是效果依然不是很理想

使用requestIdleCallback利用空闲时间渲染

requestIdleCallback 是一个浏览器 API,它允许你在浏览器空闲时执行一些低优先级的任务。我们可以使用它来优化 addBall 函数中的任务调度,以避免阻塞主线程。

另外结合DocumentFragment减少重绘共同作用优化渲染问题,下面的优化后的代码

function addBall() {// 获取要添加小球的容器元素let ballBox = document.getElementById('ballBox')// 创建一个 DocumentFragment,用于批量添加小球const fragment = document.createDocumentFragment()// 创建一个包含 10000 个任务的数组,每个任务用于创建一个小球并添加到 fragment 中const tasks = Array.from({ length: 10000 }, (_, i) => {return () => {// 创建一个 div 元素表示小球let ball = document.createElement('div')// 设置小球的文本内容为其序号ball.innerText = i + 1// 将小球添加到 fragment 中fragment.appendChild(ball)}})// 定义一个函数用于执行任务function performTasks(tasks) {// 如果任务数组为空,则将 fragment 添加到 ballBox 中if (tasks.length === 0) {ballBox.appendChild(fragment)return}// 使用 requestIdleCallback 在浏览器空闲时执行任务requestIdleCallback((deadline) => {// 当浏览器有空闲时间且任务数组不为空时,执行任务while (deadline.timeRemaining() > 0 && tasks.length > 0) {// 从任务数组中取出一个任务并执行const task = tasks.shift()task()}// 递归调用 performTasks 以继续执行剩余的任务performTasks(tasks)})}// 开始执行任务performTasks(tasks)
}

deadline.timeRemaining()requestIdleCallback 回调函数的参数 deadline 提供的方法之一。它返回当前空闲周期中剩余的毫秒数。这个方法允许你检查在当前空闲周期中还剩下多少时间可以用来执行任务

deadline.timeRemaining() 大于0表示还有空闲时间,利用这个时间来渲染小球,从而不会阻塞主线程,从而保持页面的响应性。

优化后的效果

gifimg3

可以看到,小球轻微的卡顿一下就接着继续运行

http://www.dtcms.com/a/442033.html

相关文章:

  • K230基础-几种图像处理方式
  • 鸿蒙NEXT网络管理:从“能用”到“智能”的架构演进
  • UE HTML5开发一:构建引擎以及项目发布踩坑
  • DaYe-PhotoStudio-2 v2.0.0 安装教程(64位/AMD64)详细步骤
  • 【计算机视觉】分水岭实现医学诊断
  • SAP HANA2.0数据库升级实录
  • Java-141 深入浅出 MySQL Spring事务失效的常见场景与解决方案详解(3)
  • 多功能集成工具软件,图片音视频处理一体化
  • 大型网络建站公司响应式网站的意义
  • linux使用yum安装数据库
  • php-cve篇(CVE-2019-11043CVE-2012-1823)
  • PyTorch, TensorFlow, FastAPI, LangChain, Hugging Face深度学习框架
  • 单片机学习中的一些简单总结
  • icp备案域名购买seo品牌优化
  • Oracle OCP认证考试题目详解082系列第46题
  • day85——区域和的检索(LeetCode-303)
  • 安德烈·卡帕西:深入探索像ChatGPT这样的大语言模型内容列表
  • 网站框架
  • 网站做电商销售需要注册吗有没有帮别人做网站
  • 【人工智能-03-04】20250920 人工智能第二学期课程视频《计算机网络技术 》根据视频时长刷分,手动+Python+IDM下载,更改视屏名字
  • LTU-AS:一种具备音频感知、识别、理解的大模型架构
  • Photoshop - Photoshop 工具栏(2)矩形框选工具
  • 湖南网站seo自己免费做网站有什么用
  • 理解Vivado的IP综合策略:“Out-of-Context Module Runs
  • CSS 预处理器:Sass的基本用法、核心特性
  • 【Ai改变生活】PotPlayer 史诗级更新!实时字幕生成+实时翻译!
  • 各大网站vip接口建设一个网站如何做推广
  • 深入理解ArrayList与LinkedList:Java集合框架核心对比(含实战案例+面试考点)
  • Gorm学习笔记 - 概述
  • wordpress 双分页北京朝阳区优化