让我们看看这段代码:
应用程序.tsx
import "./App.css";
import useHome from './hooks/useHome';
function App() {
useHome();
return <></>;
}
export default App;
钩子/useHome.ts
import { useEffect, useState } from "react";
const query = (): Promise<number> =>
new Promise((resolve) =>
setTimeout(() => {
resolve(1);
}, 1000),
);
const useHome = () => {
const [pageStatus, setPageStatus] = useState<string>("loading");
const [data, setData] = useState<number | null>(null);
const [deps, setDeps] = useState(data);
const queryData = async () => {
setPageStatus("loading");
try {
const pageData = await query();
setData(pageData); // cause second render
setPageStatus("normal"); // cause third render
} catch (e) {
setPageStatus("error");
}
};
useEffect(() => {
queryData();
}, []);
useEffect(() => {
setDeps(data); // cause third render
}, [data]);
console.log("@render"); // total 3 times
return {
deps,
data,
pageStatus,
};
};
export default useHome;
为什么'@render'只console.log 3次?
我预计它会渲染 4 次;
首先在初始化时渲染,
由于 setData
渲染第二个
由于 setPageStatues 而渲染第三个(这里是异步函数环境)
由于 setDeps
导致渲染
但我发现它只控制台3次...
React 是否合并了 setPageStatues 和 setDeps ?
每次重新渲染组件时,控制台日志都会触发。 (即每次组件状态发生变化时)
此外,最初的反应会在开发模式下渲染你的组件两次,但它只会在本地执行,而不是在生产版本中执行。
setData(pageData); // cause second render
setPageStatus("normal"); // cause third render
你的假设是错误的。这些不会导致重新渲染。这些队列/批处理各自的状态更新。操作完成后,将执行状态更新并重新渲染组件。