前端性能优化汇总

484 阅读6分钟
  1. 对静态资源文件采用强缓存和协商缓存

    目的:让页面第二次及以后加载更快

    扩展:描述强缓存和协商缓存(请求头和响应头字段);

    如何保证服务器资源更新后,客户端可以抛开本地缓存,从服务器获取最新的信息;

  2. 在直接操作DOM的时候,要减少DOM的重排(回流),目的:提高页面重新渲染的性能

    • 尽可能使用vue/react 等框架,避免直接操作DOM
    • 读写分离:「扩展:浏览器的渲染队列机制」
    • 样式集中修改
    • 批量新增元素,基于文档碎片或者字符串拼接等方式,统一插入到页面中
    • 尽可能使用transfrom修改样式「开启了硬件加速,不会引发回流」
    • 要操作的元素尽可能处于单独的文档流(平面)中
    • ....
  3. 减少HTTP请求的次数和大小

    目的:加快页面第一次渲染的速度,减少页面白屏等待时间

    原因:同源下允许并发的HTTP数量是有限的(大概5-7个),如果HTTP请求数过多,剩下的需要排队等待等待加载,而且因为请求次数过多,也可能导致网络通道堵塞

    • css/js资源进行合并压缩
    • css sprite雪碧图技术
    • 图片懒加载
    • 数据懒加载(异步加载):刚开始只渲染第一屏的数据,当页面渲染完,再去发送其他屏 幕的数据请求 && 分页或者上拉加载等操作
    • 服务器端开启GZIP压缩,可以使传输的内容压缩40%-60%左右
  4. 骨架屏技术方案

    目的:加快页面第一次渲染的速度

    • 「服务器骨架屏」:首屏信息基于服务器渲染(服务器返回结构/样式/数据,前提是服 务器抗压能力和处理速度强),其余屏幕信息还是交给客户端渲染!!
    • 「客户端骨架屏」:最开始加载的时候,只是用一些框框占位而已(变相的loading效 果)
  5. 基于事件委托来优化事件绑定,目的: 提高

    原因:减少堆内存和占内存的开辟,性能比一个个的做事件绑定提高40%以上;可以给动态绑 定的元素做绑定;

  6. DNS优化,目的:加快页面第一次渲染速度

    • 原则上应该减少DNS解析次数
      • 所有的资源放在同一个域名下(相同的服务器),第一次解析完会有缓存,后续再去 获取其他资源,直接从本地缓存记录获取DNS解析信息即可
    • 实际开发中,我们根据资源类型的不同,把他们放在不同的服务器上(不同的域名下)目 的:「服务器资源的合理利用,减轻服务器的压力」,这样就增加了DNS的解析次数... 在增加解析次数的基础上,我们可以基于DNS PreFetch(DNS预解析)来进行优化
      • 原理:利用link 标签的异步性,在DNS解析的同时,GUI还可以继续渲染
  7. 关于页面中的动画处理原则:能用CSS3搞定的就不用JS;即使使用JS实现动画,能用 requestAnimationFrame实现不用定时器;如果JS都搞不懂的动画,直接让产品换需求 ...

    • 定时器:到时间不一定能执行,而且requestAnimationFrame能保证时间刷新的频率与屏幕一直
  8. 关于CSS选择器的优化

    • 减少嵌套的前缀
    • 减少复杂性
    • 语义化
  9. 导入js资源的优化,目的:也可以加快页面的第一次渲染

    • js文件放在页面最底部「避免阻碍GUIde渲染」
    • 或者设置async或者defer
  10. 导入css资源的优化 目的:也可以加快页面第一次渲染

    • 优先使用内嵌是「可以减少HTTP请求」
    • 代码过多的情况下,使用外链式
    • 坚决不用导入式,因为他会阻碍GUIde渲染
  11. 使用HTTP2.0

    • HTTP2.0相对于http1.1的优势
      • 传输的内容是基于二进制来构建的,这样更加健壮
      • 请求头和响应头信息的压缩「客户端和服务器端对头的信息各自缓存一份,每次发送 请求, 没必要再加载那么多头的信息,减少HTTP传输内容的大小」
      • 服务端主动推送「发送一次请求,服务器端不仅把这次请求的内容给我,还可以把与 其相关的内容都返回」
      • 多路复用「http1.1中,基于TCP三次握手开辟的网络通道,每一次只允许一个请求 通过(其余请求要排队等待,而且容易导致线头堵塞),而HTTP2.0中一个通道可以 允许多个请求同时进行...」
  12. 减少HTML的层级嵌套,而且使用语义化标签,以此来加快DOM TREE的生成

  13. 减少页面中的冗余代码,提高代码的重复使用率「低耦合高内聚」:函数的封装-->函数式编 程(forEach用的多)和命令式编程

  14. 对不经常使用的数据做缓存,减少非必要的请求「localStorage,sessionStorage, vuex/redux」--->对ajax进行缓存

  15. 函数的防抖和节流

  16. 避免使用iframe实现页面嵌套,基于vue-router或者react-router-dom实现前端路由

  17. 尽可能使用flex布局,减少float的使用

  18. 对于数据的实时通信,避免基于定时器的Ajax轮询,采用更好的scoket,io通信机制

  19. 合理使用闭包,对于不用的堆内存及时释放。。。以此优化内存空间

  20. 少使用cookie,因为每一次向服务器发送请求,浏览器都会把内地设置的cookie传递给服 务器(哪怕这个事情是没用的)

  21. 避免死递归和死循环,因为他们都会阻碍JS进行渲染

  22. 避免内存泄漏

  23. 使用字体图标或者SVG矢量图代替位图「位图:jpg/jpeg/png/gif...都是位图 字体图标 或者矢量图除了一定程度上减少了HTTP请求、而且对于图片的渲染和自适应尺寸的调整都有 很大帮助」

  24. vue 中为了减少DOM-DIFF计算,需要对超长列表进行优化

  25. 音视频数据一定要延迟加载,否则会让页面首次渲染变慢

  26. 不要使用css表达式

  27. JS中减少对eval的使用,对于with坚决不用

  28. JS循环的性能:for/while ->ARRAY.prototype.forEach->for of->for in (性能最差)

  29. 减少使用table布局

  30. 图片使用base64

    正常图片渲染的步骤:获取图片资源->编码->渲染

    如果使用base64: 渲染

    虽然让图片渲染更快,但是导致页面中的代码“超多(e)”,不方便维护,合理利用base64

    • 后期在webpack当中,我们会直接把小图都base64了,、
    • 在图片不能做延迟加载的情况下(世界杯的大图,图片信息很重要),我们可以基于 base64来做

终极方案

如果公司有钱,以上优化都可以不做,直接把资源部署到CDN上