如docs中所述,在随后的重新渲染过程中,useState
返回的第一个值将始终是应用更新后的最新状态。但是,我有一个用例,在后续重新渲染期间,状态需要重新初始化为props中提供的初始值。
将此示例视为我的用例的简化版本:
import React from "react";
import "./styles.css";
function Counter({ initialCount, handleChange }) {
const [count, setCount] = React.useState(initialCount);
const handleClick = (counter) => {
setCount(count + counter);
handleChange(count);
};
return (
<>
<h1>Counter {count}</h1>
<button
type="button"
onClick={() => handleClick(1)}
style={{ marginRight: "8px" }}
>
Add
</button>
<button type="button" onClick={() => handleClick(-1)}>
Subtract
</button>
</>
);
}
export default function App() {
const [countOne, setCountOne] = React.useState(1);
const [countTwo, setCountTwo] = React.useState(countOne % 2);
return (
<div className="App">
<Counter
initialCount={countOne}
handleChange={(val) => setCountOne(val)}
/>
<Counter
initialCount={countTwo}
handleChange={(val) => setCountTwo(val)}
/>
</div>
);
}
您也可以选中codesandbox。
当我增加第一个计数器时,我希望第二个计数器根据第一个计数器的计数是偶数还是奇数将其重置为0或1(从原来的状态开始)。请注意,只有单向依赖,而没有任何循环一的含义;更改第二个计数器中的计数不应重置第一个计数器中的计数。
答案 0 :(得分:1)
来自react组件文档
如果您想在道具更改时“重置”某些状态,请考虑... fully uncontrolled with a key。
在要重置为其初始状态的组件上使用反应键。
当第一个countOne
更新时,您可以使用Counter
作为要重置的第二个Counter
的密钥。提供countOne % 2
作为第二个Counter
的初始值。删除countTwo
的重复状态,因为这是不必要的。并将handleChange
回调设为可选,但将 new 状态值传递给回调(即count + counter
),或使用效果来处理该回调,否则状态值不会保持同步。
function Counter({ initialCount, handleChange }) {
const [count, setCount] = React.useState(initialCount);
const handleClick = (counter) => {
setCount(count + counter);
handleChange && handleChange(count + counter);
};
// or
useEffect(() => {
handleChange && handleChange(count);
}, [count, handleChange]);
const handleClick = (counter) => {
setCount(count + counter);
};
return (
<>
<h1>Counter {count}</h1>
<button
type="button"
onClick={() => handleClick(1)}
style={{ marginRight: "8px" }}
>
Add
</button>
<button type="button" onClick={() => handleClick(-1)}>
Subtract
</button>
</>
);
}
export default function App() {
const [countOne, setCountOne] = React.useState(1);
return (
<div className="App">
<Counter
initialCount={countOne}
handleChange={setCountOne}
/>
<Counter
key={countOne}
initialCount={countOne % 2}
/>
</div>
);
}
如果您不想使用react键将其重置为初始状态,则可以在第二个useEffect
钩子中提供另一个道具作为依赖项,以重置为提供的{{1} }。
initialValue
将function Counter2({ initialCount, handleChange, reset }) {
const [count, setCount] = React.useState(initialCount);
useEffect(() => {
handleChange && handleChange(count);
}, [count, handleChange]);
useEffect(() => {
setCount(initialCount);
}, [reset, initialCount]);
const handleClick = (counter) => {
setCount(count + counter);
};
return (
<>
<h1>Counter 2: {count}</h1>
<button
type="button"
onClick={() => handleClick(1)}
style={{ marginRight: "8px" }}
>
Add
</button>
<button type="button" onClick={() => handleClick(-1)}>
Subtract
</button>
</>
);
}
传递给countOne
道具,以便在reset
更新时重置计数。
countOne