性能优化篇--Performance(工具)

1. 整体结构

从上到下分别为 4 个区域:

  1. 工具面板:包含录制,刷新页面分析,清除结果等一系列操作

  2. 概览面板:高度概括随时间线的变动,包括 CPU,NET

  3. 线程面板:例如 Network,Frames,Main 等

  4. 统计面板:精确到毫秒级的分析,以及按调用层级,事件分类的整理

2. 工具面板

工具面板常用功能:

  1. record:开始记录页面运行时性能,再次点击结束记录并生成分析报告

  2. reload page:重新加载页面并记录页面加载时的性能

  3. clear: 清空所有录制的分析内容。

  4. Screenshots:是否启用屏幕截图,启用后将会在录制时捕获每一帧的屏幕截图

  5. Memory:是否显示内存指标

  6. Collect rubbish:点击使其强制进行垃圾回收

3. 概览面板

概览面板分为CPU和NET两个区域,如果在工具面板中勾选Memory,会多出HEAP区域

1. CPU

CPU资源使用情况,CPU 中面积图如果充满色彩就表示该时间段 CPU 已达到极限,颜色与统计面板中的 Summary 颜色数据表示一致

(1)白色:表示空闲时间

(2)灰色:表示其它事件花费的时间

(3)黄色:表示 JavaScript 执行时间

(4)紫色:表示样式计算和布局(重排)时间

(5)蓝色:表示网络通信和 HTML 解析时间

(6)绿色:表示重绘时间

(7)红色:存在长任务(long task),页面卡顿

视页面情况,每种颜色(任务)占比不一样。

2. NET

每条横杠表示一种资源。深蓝色表示存在高优先级的资源请求的时间段,浅蓝色表示存在低优先级的资源请求的时间段

3. HEAP

JS Heap,JS堆内存使用情况,如果曲线一直在增长,则说明可能存在内存泄露

4. 线程面板

1. Network

表示服务器资源的加载情况。

更推荐使用NetWork面板来看

  1. 在Waterfall中,右侧离红线越远,说明请求开始的时间越晚(请求数量过多等原因)

  2. 蓝色或绿色越宽,说明内容下载或等待服务器响应时间越长(需后端优化)

  3. 灰色越宽,说明从重传开始到接收端正确响应的时间越长(如果灰色过长,往往是丢包所致)

  4. 棕色越宽,说明从客户端开始尝试建立连接,到成功建立连接所需的时间越长(网络拥堵、服务器不可达等原因)

除了Waterfall,还可以根据Size、Time列查看请求资源具体的大小和时间等信息

2. Frames

查看每秒帧数。将鼠标悬停在其中一个绿色方块上会显示该帧的耗时和 FPS,如出现红色方块则表示出现掉帧

3. Timings

  1. FP(First Paint):首屏绘制,页面刚开始渲染的时间

  2. FCP(First ContentfulPaint):首屏内容绘制,首次绘制任何文本,图像,非空白 canvas 或 SVG 的时间点

  3. DCL(DOMContentLoaded):HTML 文档加载完成

  4. L(onload):页面所有资源加载完成

  5. LCP(Largest Contentful Paint ):最大内容绘制,页面上尺寸最大的元素绘制时间

提示:加载顺序由页面决定,例如L可能在LCP之前,也可能在LCP之后

4. Main

记录了渲染进程中主线程的执行记录,是我们分析具体函数耗时最常看的面板,也是我们常说的火焰图

首先,面板中会有很多的 Task,如果是耗时长的 Task(超过50ms),其右上角会标红,这个时候,我们可以选中标红的 Task。选中后,可以看到哪些事件耗时了多少,点击压缩后的文件名,可以看到具体的代码

常见事件:

Compile Code(黄色) JavaScript代码正在被编译
Parse HTML(蓝色) Chrome执行其HTML解析算法
Recalculate Style(紫色) Chrome重新计算了元素样式
Layout(紫色) 页面布局已被执行
Paint(绿色) 合成的图层被绘制到显示画面的一个区域

简单示例:

(1)在一个长任务Task中,Parse HTML占据了较大的比重,点击源文件,定位到的内容如下所示:

使用innerHTML,浏览器都需要重新解析和渲染插入的HTML内容,会导致解析HTML的时间变长。

(2)Recalculate Style也占据了较大的比重,点击源文件,定位到的内容如下所示:

读取offsetWidth属性会导致浏览器强制进行回流操作。回流操作会重新计算页面的布局,导致重新计算样式的时间变长

5. GPU

可以直观看到何时启动 GPU 加速

6. Compositor

合成线程的执行记录,用来记录 html 绘制阶段 (Paint)结束后的图层合成操作

7. Raster

光栅化线程池,用来让 GPU 执行光栅化的任务

8. Memory

在勾选后,就会显示折线图,通过该图我们可以看到页面中的内存使用的情况,比如 JS Heap(堆),如果曲线一直在增长,则说明可能存在内存泄露。

5. 统计面板

1. Summary

表示各指标时间占用统计报表,与总览区域里面的cpu使用区域颜色一致

  1. 蓝色(Loading):表示网络通信和 HTML 解析时间

  2. 黄色(Scripting):表示 JavaScript 执行时间

  3. 紫色(Rendering):表示样式计算和布局(重排)时间

  4. 绿色(Painting):表示重绘时间

  5. 灰色(other):表示其它事件花费的时间

  6. 白色(Idle):表示空闲时间

2. Bottom-Up

可以看到各个事件消耗时间排序

这里有两列时间数据,一是"Self Time"代表任务自身执行所消耗的时间,二是"Total Time"代表此任务及其调用的附属子任务一共消耗的时间。

3. Call tree

可以看到整个事件的调用栈。Call tree 使用比较少,一般看Bottom-Up

4. Event Log

是按顺序记录的事件日志,常见的优化级别中一般用不到它

6. 示例

1. 性能分析

影响页面性能的因素有很多,比如网络请求,js执行时间,内存泄漏,页面的重排与重绘等等。这里以JS执行时间,以及如何使用performance面板排查为例。

首先,准备这样一段代码

js 复制代码
<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8" />
    <title>worker performance optimization</title>
  </head>
  <body>
    <script>
      function a() {
        let total = 0;
        for (let i = 0; i < 10 * 10000 * 10000; i++) {
          total += i;
        }
        console.log("a:", total);
      }

      a();
    </script>
  </body>
</html>

然后用无痕模式打开 chrome,无痕模式下没有插件,分析性能不会受插件影响。在performance面板中点击 reload 按钮进行性能分析。

飘红的Task即长任务,点击Task,可以在Bottom-Up中看到各个函数所耗费的时长,其中a函数耗费最久,点击右侧的a.html,可以定位到源码对应的位置

这样我们就定位到了耗时长的函数,并进行改进。

2. 性能优化

使用浏览器的 web worker进行耗时任务的计算

新建worker.js

js 复制代码
self.onmessage = (e) => {
  let total = 0;
  let num = e.data;
  for (let i = 0; i < num; i++) {
    total += i;
  }
  self.postMessage("worker返回值:" + total);
  self.close(); //发送完后关闭
};

修改a.html

js 复制代码
<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8" />
    <title>worker performance optimization</title>
  </head>
  <body>
    <script>
      function runWorker(url, num) {
        return new Promise((resolve, reject) => {
          const worker = new Worker(url);
          worker.postMessage(num);
          worker.onmessage = (e) => {
            resolve(e.data);
          };
          worker.onerror = reject; //错误处理
        });
      }

      function a() {
        //不能打开本机的文件系统,需使用网络资源
        runWorker("http://127.0.0.1:5501/worker.js", 10 * 10000 * 10000).then(
          (res) => {
            console.log("a:", res);
          }
        );
      }

      a();
    </script>
  </body>
</html>

安装VSCode插件Live Server,使用open with live Server打开a.html,并进行性能分析

可以看到Main主线程中,长任务已经没有了,多了一个Worker线程,长任务在Worker线程中执行

参考文章:

juejin.cn/post/705291...

juejin.cn/post/704680...

相关推荐
minDuck2 分钟前
ruoyi-vue集成tianai-captcha验证码
java·前端·vue.js
小政爱学习!23 分钟前
封装axios、环境变量、api解耦、解决跨域、全局组件注入
开发语言·前端·javascript
魏大帅。28 分钟前
Axios 的 responseType 属性详解及 Blob 与 ArrayBuffer 解析
前端·javascript·ajax
花花鱼34 分钟前
vue3 基于element-plus进行的一个可拖动改变导航与内容区域大小的简单方法
前端·javascript·elementui
k093338 分钟前
sourceTree回滚版本到某次提交
开发语言·前端·javascript
EricWang13581 小时前
[OS] 项目三-2-proc.c: exit(int status)
服务器·c语言·前端
September_ning1 小时前
React.lazy() 懒加载
前端·react.js·前端框架
web行路人1 小时前
React中类组件和函数组件的理解和区别
前端·javascript·react.js·前端框架
番茄小酱0011 小时前
Expo|ReactNative 中实现扫描二维码功能
javascript·react native·react.js
子非鱼9211 小时前
【Ajax】跨域
javascript·ajax·cors·jsonp