讲下useEffect 和 useLayoutEffect

122 阅读2分钟

内容大部分来自学习神光的react小册

首先绝大多数情况下,你把 useEffect 换成 useLayoutEffect 也一样

后者的出现原因是 js执行和渲染是阻塞的

useEffect的effect函数会在dom之后异步执行:

这里解释js异步执行:

在 JavaScript 中,异步执行是一种执行方式,它允许程序在执行某些操作时不会阻塞后续代码的执行,而是在操作完成后通过回调函数、Promise 或者 async/await 等方式来处理结果。例如,当进行网络请求或者读取文件等耗时操作时,可以使用异步执行,这样不会导致页面或程序的卡顿,提高了程序的响应性和性能。

由于渲染的间隔是固定的,而 js 的任务在这些渲染的间隔中执行。

所以异步执行的 effect 逻辑就有两种可能:

这样就导致有的时候页面会出现闪动,因为第一次渲染的时候的 state 是之前的值,渲染完之后执行 effect 改了 state,再次渲染就是新的值了。

useLayoutEffect可以解决闪动,它和 useEffect 的区别是它的 effect 执行是同步的,也就是在同一个任务里

但是也有弊端,如果effect函数执行太久,就会阻塞渲染了。

超过 50ms 的任务就被称作长任务,会阻塞渲染,导致掉帧:

所以一般用effect逻辑异步执行就好了。也就是说,绝大多数用useEffect。它能避免因为 effect 逻辑执行时间长导致页面卡顿(掉帧)。

但如果你遇到闪动的问题比较严重,那可以用 useLayoutEffect,但要注意 effect 逻辑不要执行时间太长