我经常使用类组件,其中我们有 getderivedstatefromprops 方法,但是如何处理功能组件中的那些派生状态,所以有人指导我如何处理即将到来的派生状态?
2 回答
这有很多方法可以做到,但最好的方法是根据情况而定。
选项 1:只需使用const
当该值不受事件影响、不是繁重的计算并且不需要作为可比较的参考传递给更向下的组件/挂钩时,这种方法效果最好。
const Example = ({price, quantity}) => {
const totalPrice = price * quantity;
return (
<div>
{totalPrice}
</div>
);
}
此方法将导致每次组件重新渲染时重新计算该值,但不包括用于比较依赖项和存储随useMemo
.
如果计算的是非原始类型,例如对象,那么每次重新计算对象时,它都会收到一个新的引用,从而导致 React 的浅层比较失败。根据您对派生值所做的操作,这可能意味着这是或不是问题。
选项 2:使用useMemo
当该值不受事件影响并且是繁重的计算或需要作为可比较的参考传递给更向下的组件/挂钩时,此方法效果最佳。
const Example = ({price, quantity}) => {
const totalPrice = useMemo(() => {
return price * quantity;
}, [price, quantity]
return (
<div>
{totalPrice}
</div>
);
}
每当依赖数组(在示例中)中的值发生变化(参考比较)时,该方法将导致重新计算值[price, quantity]
,这确实包括比较依赖数组并确定是否需要重新计算的计算开销以及内存开销从存储重新渲染之间的值。
可以进行性能测试以检查是否仅使用 aconst
或 usinguseMemo
对于每个场景更有效。
选项 3:使用useState
和useEffect
这对于将受事件影响的值最有效,当需要将值作为可比较的参考传递或进行大量计算时,它也很有用。
const Example = ({price, quantity}) => {
const [totalPrice, setTotalPrice] = useState(price * quantity);
useEffect(() => {
setTotalPrice(price * quantity);
}, [price, quantity]
return (
<div>
{totalPrice}
<div onClick={() => setTotalPrice(current => current * 2)}>
Double Total Price
</div>
</div>
);
}
setState
每当调用函数时(setTotalPrice
在示例中),此方法将导致存储一个新值。为了实现基于 props 更改的更新,useEffect
可以与依赖数组([price, quantity]
在示例中)一起使用,该数组将在相关属性更改时运行(参考比较)。
该方法还允许该值受到能够调用该setState
函数的其他事件的影响(参见onClick
示例中的 )。
结论
这不是一个完整的列表,但它涵盖了基本选项。
使用 React 外部的代码或使用 React 的 Context 可以进行更复杂的状态管理。
使用useEffect
钩子,你可以在这里阅读更多