React提取嵌套数组serviceType去重后设置state不生效的解决方法
问题核心原因
你的useEffect依赖数组为空,只会在组件首次挂载时执行1次:
- 如果父组件传递的
options是异步获取的,首次挂载时options还未拿到完整数据,createNewArray计算得到的是空值,后续options更新也不会重新触发计算 - 即使
options是同步传入,空依赖也会隐藏createNewArray依赖options的逻辑,属于React Hook规则中明确的依赖缺失问题
解决方案
- 把
options加入useEffect依赖数组,只要options发生变化就重新计算去重后的数组 - 建议把state初始值设为空数组
[],避免后续渲染时处理null的边界情况 - 可选优化:原
createNewArray中没有用到map的返回值,属于对map方法的误用,遍历操作可以改用forEach,或者用flatMap简化写法
修改后代码示例
const MenuOptions = ({ options }) => { const [array, setArray] = useState([]) const createNewArray = () => { // 简化写法,直接打平提取所有serviceType后去重 const optionsArr = options.flatMap(option => option.services.map(service => service.serviceType) ) return [...new Set(optionsArr)] } useEffect(() => { setArray(createNewArray()) }, [options]) // 加入options作为依赖 // 渲染option的逻辑示例 return ( <select> {array.map(type => ( <option key={type} value={type}>{type}</option> ))} </select> ) }
额外优化建议
如果你的options不会频繁变更,也可以不用把结果存在state里,直接在渲染时计算即可,减少不必要的state更新:
const MenuOptions = ({ options }) => { // 直接计算,React会在options变化时自动重新计算 const uniqueServiceTypes = [...new Set( options.flatMap(option => option.services.map(s => s.serviceType)) )] return ( <select> {uniqueServiceTypes.map(type => ( <option key={type} value={type}>{type}</option> ))} </select> ) }
内容的提问来源于stack exchange,提问作者Ben Shekhtman
相关产品推荐
相关产品推荐

