React Functional Component - 在 const vs state 中存储一些 prop 计算
React Functional Component - Store some prop calculation in const vs state
我有一个只渲染一次然后被销毁的组件,
我已经实现了“Comp3”方式。
使用“useEffect”计算 str 和我收到的 num 值作为 prop,然后使用“useEffect”setter 存储结果以便在 html 中使用结果。
//Let say this function is inside the functional component
function numToStr(num:number):string{
switch(num){
case 1:
return "One";
case 2:
return "Two";
...
}
}
function Comp1({num:number}){
const numAsStr = numToStr(num);
return <span>{numAsStr}</span>
}
function Comp2({num:number}){
const [numAsStr] = useState(numToStr(num));
return <span>{numAsStr}</span>
}
function Comp3({num:number}){
const [numAsStr,setNumAsStr] = useState();
useEffect(()=>{
setNumAsStr(numToStr(num));
},[])
return <span>{numAsStr}</span>
}
function Comp4({num:number}){
const numAsStr = useMemo(()=>numToStr(num),[]);
return <span>{numAsStr}</span>
}
我的问题是:
就最佳实践/“反应方式”而言,最佳解决方案是什么?
每个实施如何影响性能?
我知道组件只渲染一次这一事实是否会影响我选择实现的方式?
或者我是否应该将此组件视为我不知道它应该被渲染一次并且在这种情况下仍然支持“观察”正在更改的道具的选项? (将其添加到 useEffect / useMemo 数组)
谢谢!
如果 strToNum
所做的计算很便宜(就像在您的简化示例中那样),那么 Comp1
中的方法可能是最好和最简单的。每次组件重新呈现时,它们都会 运行,因此它们始终是最新的。
如果计算量很大,建议的处理方法是 the useMemo
hook,就像您的 Comp4
示例一样。但是,您需要确保在 dependents 数组中包含 num
输入变量,以便在 num
更改时重新计算 numAsStr
。例如:
function Comp4({num:number}){
const numAsStr = useMemo(()=>numToStr(num),[num]);
return <span>{numAsStr}</span>
}
像在 Comp2
中那样使用 useState
只会在初始渲染中 运行 numToStr
,所以如果 num
你会得到陈旧的值永远改变。
像在 Comp3
中那样使用 useEffect
会引入不必要的双重渲染 - 例如它首先呈现没有 numAsStr
的值,然后再次呈现。
我知道你说过你目前确定它永远不会再重新呈现 - 所以上面提到的一些 downsides/gotchas 可能不适用于这种情况(然后我会选择 Comp1
方法,因为它更简单)但根据我的经验,最好不要做出这样的假设 - 你(或队友)会在一个月内尝试重构某些东西时记得吗?
我有一个只渲染一次然后被销毁的组件, 我已经实现了“Comp3”方式。
使用“useEffect”计算 str 和我收到的 num 值作为 prop,然后使用“useEffect”setter 存储结果以便在 html 中使用结果。
//Let say this function is inside the functional component
function numToStr(num:number):string{
switch(num){
case 1:
return "One";
case 2:
return "Two";
...
}
}
function Comp1({num:number}){
const numAsStr = numToStr(num);
return <span>{numAsStr}</span>
}
function Comp2({num:number}){
const [numAsStr] = useState(numToStr(num));
return <span>{numAsStr}</span>
}
function Comp3({num:number}){
const [numAsStr,setNumAsStr] = useState();
useEffect(()=>{
setNumAsStr(numToStr(num));
},[])
return <span>{numAsStr}</span>
}
function Comp4({num:number}){
const numAsStr = useMemo(()=>numToStr(num),[]);
return <span>{numAsStr}</span>
}
我的问题是:
就最佳实践/“反应方式”而言,最佳解决方案是什么?
每个实施如何影响性能?
我知道组件只渲染一次这一事实是否会影响我选择实现的方式?
或者我是否应该将此组件视为我不知道它应该被渲染一次并且在这种情况下仍然支持“观察”正在更改的道具的选项? (将其添加到 useEffect / useMemo 数组)
谢谢!
如果 strToNum
所做的计算很便宜(就像在您的简化示例中那样),那么 Comp1
中的方法可能是最好和最简单的。每次组件重新呈现时,它们都会 运行,因此它们始终是最新的。
如果计算量很大,建议的处理方法是 the useMemo
hook,就像您的 Comp4
示例一样。但是,您需要确保在 dependents 数组中包含 num
输入变量,以便在 num
更改时重新计算 numAsStr
。例如:
function Comp4({num:number}){
const numAsStr = useMemo(()=>numToStr(num),[num]);
return <span>{numAsStr}</span>
}
像在 Comp2
中那样使用 useState
只会在初始渲染中 运行 numToStr
,所以如果 num
你会得到陈旧的值永远改变。
像在 Comp3
中那样使用 useEffect
会引入不必要的双重渲染 - 例如它首先呈现没有 numAsStr
的值,然后再次呈现。
我知道你说过你目前确定它永远不会再重新呈现 - 所以上面提到的一些 downsides/gotchas 可能不适用于这种情况(然后我会选择 Comp1
方法,因为它更简单)但根据我的经验,最好不要做出这样的假设 - 你(或队友)会在一个月内尝试重构某些东西时记得吗?