Was*_*aya 16 reactjs react-hooks
我可以在 useEffect 中调用另一个单独的函数吗?
我正在 iuseEffect 中调用另一个函数,但在保存文件后,它会自动将该函数添加到 useEffect 的数组参数中。
请参阅下面的代码以正确理解。
保存文件前:
useEffect(() => {
getData()
console.log("useEffect ran...");
}, [query]);
function getData() {
fetch(`https://jsonplaceholder.typicode.com/${query}`)
.then(response => response.json())
.then(json => setData(json));
}
Run Code Online (Sandbox Code Playgroud)
保存文件后:
useEffect(() => {
getData();
console.log("useEffect ran...");
}, [getData, query]);
function getData() {
fetch(`https://jsonplaceholder.typicode.com/${query}`)
.then(response => response.json())
.then(json => setData(json));
}
Run Code Online (Sandbox Code Playgroud)
它一次又一次地运行。
Dan*_*elK 23
TL; DR 使用 useCallback()
首先,让一个函数成为依赖是非常危险的。如果该函数导致状态更改,则随后的重新渲染将再次调用该函数(通过 useEffect)...并开始无限循环。
正如许多人在这里建议的那样,您可以做的一件事是在 useEffect() 方法本身内创建函数。
useEffect(() => {
function getData() {
fetch(`https://jsonplaceholder.typicode.com/${query}`)
.then(response => response.json())
.then(json => setData(json));
}
}
getData();
console.log("useEffect ran...");
}, [query]);
}
Run Code Online (Sandbox Code Playgroud)
或者干脆
useEffect(() => {
(() => {
fetch(`https://jsonplaceholder.typicode.com/${query}`)
.then(response => response.json())
.then(json => setData(json)
)();
}, [query]);
}
Run Code Online (Sandbox Code Playgroud)
话虽如此,有时您仍然希望在 useEffect 之外为code-reuse声明函数。这次您需要确保它不会在每次渲染期间重新创建。为此,您可以
在组件外声明函数 - 这迫使您将所有变量作为参数传递......这是一个痛苦
把它包在里面useMemo()或useCallback()
这是一个例子
const getData = useCallback(()=>{...}, []);
Run Code Online (Sandbox Code Playgroud)
sve*_*hui 17
由于您getData在 React 组件中声明了该函数,它将在每次渲染时重新创建,因此效果的依赖关系在每次渲染时都会发生变化。这就是为什么在每次渲染上执行效果的原因。
为了防止这种情况,您应该getData在组件外部声明函数,然后传递查询。像这样:
function getData(query) {
return fetch(`https://jsonplaceholder.typicode.com/${query}`)
.then(response => response.json());
}
function YouComponent({ query }) {
...
useEffect(() => {
getData(query).then(setData);
console.log("useEffect ran...");
}, [query]);
...
Run Code Online (Sandbox Code Playgroud)
PS:我不确定 eslint 插件在这样做时是否会自动将 getData 添加到依赖项中,但即使这样做也不会造成伤害。
接受的答案在某种程度上具有误导性。显然,在组件内部定义函数会在每次渲染时重新创建。但这并不意味着在使用 useEffect hook 内部时它会在每次渲染中重新调用。
保存文件代码后的关键问题是您正在监视 getData。由于它在每个渲染上重新创建,因此 useEffect 接受它作为更改,从而导致您在每个渲染上重新运行。简单的修复方法是不观看 getData。
但显然,正如已接受的答案中所建议的那样。更好的做法是将函数分离到组件之外,这样它就不会在每次渲染时重新创建。
坦率地说,如果我是你,我不会只为 fetch 定义函数:
useEffect(() => {
fetch(`https://jsonplaceholder.typicode.com/${query}`)
.then(response => response.json())
.then(json => setData(json));
}, [query]); // only re-run on query change
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
39805 次 |
| 最近记录: |