【性能优化】常见性能优化方法
zh-rocco opened this issue · comments
性能优化
**:性能优化先优化性能瓶颈(短板),具体问题具体分析。
性能优化的最关键点是首屏。
用户交互时也会出现性能瓶颈:大量 dom 更新(react 性能优势在这,vdom 可以减少不必要的 dom 更新),频繁的页面的重排,动画(动画写的不好性能会很差,比如频繁的页面的重排)。
常见的优化方法
客户端优化
-
加载优化(网络方面)
- 减少 HTTP 请求
- 合并 CSS、JS
- 使用雪碧图
- 小图转 base64,可以受益于 gzip
- 减少资源体积
- 压缩 CSS、JS
- 压缩图片
- 减少 HTTP 请求
-
渲染和 DOM 操作方面
- 在网页初步加载时,获取到 HTML 文件之后,最初的工作是构建 DOM 和构建 CSSOM 两个树,之后将他们合并形成渲染树,最后对其进行打印
- 优化网页渲染
- CSS 放在头部
- 保证解析 DOM 的同时解析 CSS
- CSS(外链或内联)会阻塞整个 DOM 渲染,但是不会阻塞 DOM 解析
- JS 放在 body 结束标签前或者异步
- JS(外链或内联)会阻塞后续的 DOM 解析,DOM 渲染也会被阻塞
- CSS 放在头部
- 优化 DOM 操作
- 避免在 document 上直接进行频繁的 DOM 操作(减少回流和重绘)
- 使用 className 代替大量的内联样式修改(减少回流和重绘)
- 对于复杂的 UI 元素,设置 position 为 absolute 或 fixed(减少回流和重绘)
- 避免强制性同步布局(减少回流和重绘)
- 比如给某个元素添加了一个类,然后再读取布局信息,这个时候为了获得真实的布局信息,浏览器需要强制性对页面进行布局
- 批量操作 DOM(减少回流和重绘)
- 尽量使用 CSS 动画
- 尽量减少 CSS 表达式(expression)
- 使用 requestAnimationFrame 代替 setInterval 操作
- 使用事件代理
- 操作细节注意
- 避免图片或者 iframe 使用空 src
- 避免使用空的 src 属性可以缩减浏览器首屏渲染的时间,因为浏览器在渲染过程中会把 src 属性中的空内容进行加载,直至加载失败,影响 DOMContentLoaded 与 Loaded 事件之间的资源准备过程,拉长了首屏渲染所用的时间;但空的 href 属性对首屏渲染的影响比较小
- 在 CSS 属性为 0 时,去掉单位
- 禁止图像缩放
- 正确的 CSS 前缀,autoprefix
- 移除空的 CSS 规则
- 对于可继承的属性,尽量使用继承
- 缩短 CSS 选择器,BEM
- 避免图片或者 iframe 使用空 src
- 移动端优化
- 长列表滚动优化,-webkit-overflow-scrolling: touch,视口之外 visibility: hidden
- 函数防抖和函数节流
- 使用 touchstart、touchend 代替 click,或者 fastclick
- 开启 GPU 渲染加速,transform3d、transformZ、will-change
-
数据方面
- 图片加载处理
- 图片预加载
- 图片懒加载
- 首屏加载时显示进度条
- 异步请求的优化
- 使用正常的 json 数据格式进行交互
- 缓存常用的不变数据
- 数据埋点和统计
- 组件懒加载、预加载
- 合理控制 cookie 的大小(每次请求都会包含 cookie)
- 图片加载处理
服务端优化
-
服务器开启 gzip
-
缓存
- DNS 缓存,将资源分配到恰当数量的主机名;以减少 DNS 查询
- 避免重定向,减少多余的中间访问
- CDN 加速
- HTTP 缓存:设定缓存时间
- cache-control
- public:响应被缓存,并且在多用户间共享
- private:默认值,响应只能够作为私有的缓存(e.g., 在一个浏览器中),不能再用户间共享
- no-cache:响应不会被缓存,而是实时向服务器端请求资源
- max-age:数值,单位是秒,从请求时间开始到过期时间之间的秒数。基于请求时间
- date:生成消息的具体时间和日期
- expires:指定了在浏览器上缓冲存储的页距过期还有多少时间,等同 Cache-control 中的 max-age 的效果,如果同时存在,则被 Cache-Control 的 max-age 覆盖。若把其值设置为 0,则表示页面立即过期。并且若此属性在页面当中被设置了多次,则取其最小值
- last-modified / if-modified-since:本地文件在服务器上的最后一次修改时间。缓存过期时把浏览器端缓存页面的最后修改时间发送到服务器去,服务器会把这个时间与服务器上实际文件的最后修改时间进行对比,如果时间一致,那么返回 304,客户端就直接使用本地缓存文件
- etag / if-none-match
- (EntityTags)是 URL 的 tag,用来标示 URL 对象是否改变,一般为资源实体的哈希值。和 Last-Modified 类似,如果服务器验证资源的 ETag 没有改变(该资源没有更新),将返回一个 304 状态告诉客户端使用本地缓存文件。Etag 的优先级高于 Last-Modified,Etag 主要为了解决 Last-Modified 无法解决的一些问题
- 文件也许会周期性的更改,但是他的内容并不改变,不希望客户端重新加载
- If-Modified-Since 能检查到的粒度是 s 级
- 某些服务器不能精确的得到文件的最后修改时间
- cache-control
-
负载均衡