3 回答

TA貢獻(xiàn)1797條經(jīng)驗(yàn) 獲得超6個(gè)贊
afimport React, { useCallback, useState, useEffect, useRef } from "react";
import "./styles.css";
export default function App() {
? let [count, setCount] = useState(0);
? useInterval(() => {
? ? setCount(count + 1);
? }, 1000);
? return <div className="App">{count}</div>;
}
function useInterval(callback, delay) {
? const savedCallback = useRef();
? // Remember the latest callback.
? useEffect(() => {
? ? savedCallback.current = callback;
? }, [callback]);
? // Set up the interval.
? useEffect(() => {
? ? function tick() {
? ? ? savedCallback.current();
? ? }
? ? if (delay !== null) {
? ? ? let id = setInterval(tick, delay);
? ? ? return () => clearInterval(id);
? ? }
? }, [delay]);
}
工作代碼沙箱
更新
正如 keith 建議的那樣,不要將函數(shù)傳遞給數(shù)組 deps,如下所示。
import React, { useState, useEffect } from "react";
import "./styles.css";
export default function App() {
? const [count, setCount] = useState(0);
? useEffect(() => {
? ? const interval = setInterval(() => {
? ? ? setCount((count) => count + 1);
? ? }, 1000);
? ? return () => {
? ? ? clearInterval(interval);
? ? };
? }, []);
? return <div>{count}</div>;
}

TA貢獻(xiàn)1802條經(jīng)驗(yàn) 獲得超10個(gè)贊
還是不太清楚為什么可以通過(guò)[]
也許需要更多解釋,不幸的是評(píng)論太多,所以我發(fā)布了這個(gè)。
要回答這個(gè)問(wèn)題,我們需要退一步,首先問(wèn),依賴數(shù)組的意義是什么?簡(jiǎn)單的答案是 useEffect 中任何依賴于某些內(nèi)容的內(nèi)容,如果從需要不同處理的 useState 或 Props 進(jìn)行更改,則需要將其放入數(shù)組中。
例如,如果您有一個(gè)僅顯示用戶配置文件的組件,但獲取此信息是異步的,因此需要 useEffect。它可能看起來(lái)像這樣 ->
<UserProfile userId={userId}/>
現(xiàn)在的問(wèn)題是,如果我們[]
作為依賴項(xiàng)傳遞,則 useEffect 不會(huì)為新的 userId 重新觸發(fā),因此 props 可能會(huì)說(shuō)userId = 2
,但我們當(dāng)前存儲(chǔ)在狀態(tài)中的數(shù)據(jù)是 for userId = 1
,.. 所以對(duì)于這樣的東西[props.userId]
完全有道理。
那么回到 OP 的組件,<App/>
這里有什么會(huì)改變的?好吧,這不是道具,因?yàn)闆](méi)有被傳遞。那么count
您可能會(huì)問(wèn),我們?cè)俅螁?wèn)自己這個(gè)問(wèn)題,計(jì)數(shù)狀態(tài)是否保證 setInterval 的新實(shí)例被銷毀/創(chuàng)建?當(dāng)然,這里的答案是否定的,因此[]
在這里傳遞是完全有意義的。
希望這是有道理的。

TA貢獻(xiàn)1812條經(jīng)驗(yàn) 獲得超5個(gè)贊
清除卸載時(shí)的間隔
useEffect(() => {
let id;
const setId = () => {
id = setInterval(() => {
setCount((count) => count + 1);
}, 1000);
};
setId();
return () => clearInterval(id);
}, []);
添加回答
舉報(bào)