前端性能优化

二叶草 2020年2月4日14:09:11优化评论阅读模式

从广义的层面来看,就不仅限于程序内部了,因为造成系统性能问题的瓶颈很可能来源于方方面面,而这种情况往往是性能调优很普遍的情况

前端性能优化

从狭义的范畴来看,性能调优主要是指通过修改软件程序逻辑、结构等技术手段提升软件产品的各项性能指标,如响应时间等

  1. 性能的参考指标

  2. 执行时间:一段代码从开始运行到运行结束所使用的时间。

  3. CPU时间:(算法)函数或者线程占用CPU的时间。

  4. 内存分配:程序在运行时占用的内存空间。

  5. 磁盘吞吐量:描述I/O的使用情况。

  6. 网络吞吐量:描述网络的使用情况。

  7. 响应时间:系统对某用户行为或者动作做出响应的时间。响应时间越短,性能好。

阮一峰性能优化(浏览器的渲染机制、重排、重绘)

要理解网页性能为什么不好,就要了解网页是怎么生成的。网页的生成过程,大致可以分成五步。

前端性能优化

 

  1. HTML代码转化成DOM

  2. CSS代码转化成CSSOM(CSS Object Model)

  3. 结合DOM和CSSOM,生成一棵渲染树(包含每个节点的视觉信息)

  4. 生成布局(layout),即将所有渲染树的所有节点进行平面合成

  5. 将布局绘制(paint)在屏幕上

这五步里面,第一步到第三步都非常快,耗时的是第四步和第五步。

"生成布局"(flow)和"绘制"(paint)这两步,合称为"渲染"(render)。

前端性能优化

 

 
  • 样式表越简单,重排和重绘就越快。

  • 重排和重绘的DOM元素层级越高,成本就越高。

  • table元素的重排和重绘成本,要高于div元素

提高性能的九个技巧
  1. 第一条是上一节说到的,DOM 的多个读操作(或多个写操作),应该放在一起。不要两个读操作之间,加入一个写操作。

  2. 第二条,如果某个样式是通过重排得到的,那么最好缓存结果。避免下一次用到的时候,浏览器又要重排。

  3. 第三条,不要一条条地改变样式,而要通过改变class,或者csstext属性,一次性地改变样式。

  4. 第四条,尽量使用离线DOM,而不是真实的网面DOM,来改变元素样式。比如,操作Document Fragment对象,完成后再把这个对象加入DOM。再比如,使用 cloneNode() 方法,在克隆的节点上进行操作,然后再用克隆的节点替换原始节点。

  5. 第五条,先将元素设为display: none(需要1次重排和重绘),然后对这个节点进行100次操作,最后再恢复显示(需要1次重排和重绘)。这样一来,你就用两次重新渲染,取代了可能高达100次的重新渲染。

  6. 第六条,position属性为absolute或fixed的元素,重排的开销会比较小,因为不用考虑它对其他元素的影响。

  7. 第七条,只在必要的时候,才将元素的display属性为可见,因为不可见的元素不影响重排和重绘。另外,visibility : hidden的元素只对重绘有影响,不影响重排。

  8. 第八条,使用虚拟DOM的脚本库,比如React等。

  9. 第九条,使用 window.requestAnimationFrame()、window.requestIdleCallback() 这两个方法调节重新渲染(详见后文)。

性能优化指南

依据数据而不是凭空猜测

这是性能优化的第一原则,当我们怀疑性能有问题的时候,应该通过测试、日志、profillig来分析出哪里有问题,有的放矢,而不是凭感觉、撞运气。

忌过早优化

在我的工作环境(以及典型的互联网应用开发)与编程模式下,追求的是快速的迭代与试错,过早的优化往往是无用功。而且,过早的优化很容易拍脑袋,优化的点往往不是真正的性能瓶颈。

忌过度优化

性能优化的目标是追求合适的性价比。

在不同的阶段,我们对系统的性能会有一定的要求,比如吞吐量要达到多少多少。如果达不到这个指标,就需要去优化。如果能满足预期,那么就无需花费时间精力去优化,比如只有几十个人使用的内部系统,就不用按照十万在线的目标去优化。而且,后面也会提到,一些优化方法是“有损”的,可能会对代码的可读性、可维护性有副作用。这个时候,就更不能过度优化。

深入理解业务

代码是服务于业务的,也许是服务于最终用户,也许是服务于其他程序员。不了解业务,很难理解系统的流程,很难找出系统设计的不足之处。

性能优化的层次

按照我的理解可以分为需求阶段,设计阶段,实现阶段;越上层的阶段优化效果越明显,同时也更需要对业务、需求的深入理解。

需求阶段

需求是为了解决某个问题,问题是本质,需求是解决问题的手段。

需求分析对性能优化有什么帮助呢,第一,为了达到同样的目的,解决同样问题,也许可以有性能更优(消耗更小)的办法。这种优化是无损的,即不改变需求本质的同时,又能达到性能优化的效果;第二种情况,有损的优化,即在不明显影响用户的体验,稍微修改需求、放宽条件,就能大大解决性能问题。PM退步一小步,程序前进一大步。

需求讨论也有助于设计时更具扩展性,应对未来的需求变化。

网络加载类

  1. 首屏数据请求提前,避免JavaScript文件加载后才请求数据

  2. 首屏加载和按需加载,非首屏内容滚屏加载,保证首屏内容最小化

  3. 模块化资源并行下载

  4. inline首屏必备的CSS和JavaScript

  5. meta dns prefetch设置DNS预解析

  6. 资源预加载

  7. 合理利用MTU策略

缓存类

  1. 合理利用浏览器缓存(http缓存、app缓存、浏览器缓存)

  2. 静态资源离线方案

图片类

  1. 图片压缩处理(裁剪)

  2. 使用较小的图片,合理使用base64内嵌图片

在页面使用的背景图片不多且较小的情况下,可以将图片转化成base64编码嵌入到HTML页面或CSS文件中,这样可以减少页面的HTTP请求数。需要注意的是,要保证图片较小,一般图片大小超过2KB就不推荐使用base64嵌入显示了。

  1. 使用更高压缩比格式的图片

  2. 图片懒加载

  3. 使用Media Query或srcset根据不同屏幕加载不同大小图片

  4. 使用iconfont代替图片图标

  5. 定义图片大小限制

加载的单张图片一般建议不超过30KB,避免大图片加载时间长而阻塞页面其他资源的下载,因此推荐在10KB以内。如果用户上传的图片过大,建议设置告警系统,帮助我们观察了解整个网站的图片流量情况,做出进一步的改善。

架构协议类

  1. ssr

  2. seo优化

  3. 减少白屏时间

  4. 利用服务端缓存

设置max-age|expires进行优化网站

网页的缓存是由 HTTP 消息头中的 “Cache-control” 来控制的,常见的取值有 private、no-cache、max-age、must-revalidate 等,默认为private。

  1. 打开新窗口

如果指定cache-control的值为private、no-cache、must-revalidate,那么打开新窗口访问时都会重新访问服务器。而如果指定了max-age值,那么在此值内的时间里就不会重新访问服务器

Cache-control: max-age=5

// 表示当访问此网页后的5秒内再次访问不会去服务器。
  1. 在地址栏回车

如果值为private或must-revalidate(和网上说的不一样),则只有第一次访问时会访问服务器,以后就不再访问。如果值为no-cache,那么每次都会访问。如果值为max-age,则在过期之前不会重复访问。

  1. 按后退按扭

如果值为private、must-revalidate、max-age,则不会重访问,而如果为no-cache,则每次都重复访问

  1. 按刷新按扭

无论为何值,都会重复访问

 

本文来源于:前端性能优化-变化吧门户
特别声明:以上文章内容仅代表作者本人观点,不代表变化吧门户观点或立场。如有关于作品内容、版权或其它问题请于作品发表后的30日内与变化吧联系。

在寻找靠谱的建站服务?

提供建站全方位托管服务,告诉我你的需求,剩下的交给我帮你处理,建站过程中碰到的任何小问题免费处理,网站所有数据由你自己掌握,还提供网站SEO指导,犹豫什么呢?联系我吧。

 

  • 赞助本站
  • 微信扫一扫
  • weinxin
  • 加入Q群
  • QQ扫一扫
  • weinxin
二叶草
nginx解析漏洞 优化

nginx解析漏洞

phpstudy(小皮模板存在nginx解析漏洞) 影响版本 phptsuy8.1.07的Nginx1.5.11版本影响版本 phptsuy8.1.07的Nginx1.5.11版本 phpstudy介...
网站SEO优化基础流程(新手必看) 优化

网站SEO优化基础流程(新手必看)

宝塔面板搭建一个获取网站的Favicon图标的APIgetFavicon是一个可以获取网站的Favicon图标并显示在你的网页上的项目。安装方法很简单,属于开箱即食。这篇文章还是基于宝塔面板来搭建。 ...

发表评论