React Native中如何实例化、存储和修改class类变量?
问题核心分析
你当前使用var存储类实例的方案完全不可用,这也是你在useEffect中赋值后依然拿到undefined的根本原因:
函数组件每次渲染都会独立执行整个函数体,每次渲染都会重新声明一个初始值为undefined的aInstance变量,而useEffect是在渲染完成后才异步执行的,你在effect中赋值的只是当次渲染作用域下的aInstance,下一次渲染时变量会被重置为新的undefined,组件内其他同步逻辑也永远拿不到effect里赋值的实例。
最优方案选择
你提到的state不适用的判断部分正确:类内部修改自身属性确实不需要调用setState,也不会触发组件重渲染,但是把类实例存在state中本身没有功能性问题,只是不属于最优选择——因为你不需要在实例变更时触发组件重渲染,使用state会带来不必要的开销。
这个场景下最优的存储方案是React提供的useRef:
useRef的.current属性是跨渲染周期持久化存储的,不会因为组件重新渲染被重置- 修改
.current属性不会触发组件重渲染,完全符合存储可变、无需触发重渲染的类实例的需求
修改后的示例代码
... import { A } from './A' import { useRef, useEffect } from 'react' export const Acomponent = () => { // 初始化ref,初始值设为null const aInstanceRef = useRef(null); const apiObject = apiCall(); // 调用某接口 useEffect(() => { if(apiObject.status === "success"){ aInstanceRef.current = new A(apiObject.data); // 此处访问aInstanceRef.current即可拿到正常的实例 } }, [apiObject]); // 其他位置需要调用类方法时,直接访问ref.current即可 const handleOperate = () => { // 调用前建议判空,避免接口请求完成前调用报错 aInstanceRef.current?.someClassMethod() } }
额外注意点
- 如果后续有逻辑需要感知类实例初始化完成的时机,可以单独加一个布尔类型的state标记实例是否初始化完成,修改这个state即可触发对应的重渲染/副作用执行
- 如果组件卸载时需要执行类实例的销毁逻辑,可以在useEffect的清理函数中调用类的销毁方法:
useEffect(() => { if(apiObject.status === "success"){ aInstanceRef.current = new A(apiObject.data); } // 清理函数,组件卸载/依赖变更时执行 return () => { aInstanceRef.current?.destroy() } }, [apiObject])
内容的提问来源于stack exchange,提问作者TyGuy96
相关产品推荐
相关产品推荐

