React Native重构遇Cannot call a class as a function报错咨询
异常原因
TypeError: Cannot call a class as a function 触发的核心原因是你把React Navigation 4 中createAppContainer生成的类组件,错误地当作普通函数调用了,常见触发场景有两种:
- 照搬类组件时期把组件引用存在state的反模式,转函数组件后state中存储的组件引用丢失/被错误包装,渲染时被当作普通函数执行
- 渲染导航容器时没有用JSX语法,直接写了函数调用形式的
AppContainer()而非JSX形式的<AppContainer />
核心疑问解答
函数组件不支持将组件引用存在state中再取出渲染,这种写法本身违反React渲染规则:组件本身是静态的渲染单元,不属于会随交互变化的状态范畴,不管是类组件还是函数组件,把组件存在state里渲染都是不推荐的反模式,类组件阶段能运行只是未触发校验的侥幸情况。
修复步骤
- 不要将
createAppContainer生成的导航容器存入state,直接在组件作用域顶层完成导航容器的创建
import { createAppContainer } from 'react-navigation'; import { createStackNavigator } from 'react-navigation-stack'; // 路由配置 const AppNavigator = createStackNavigator({ Home: { screen: HomePage }, // 其他页面配置 }); // 顶层创建导航容器,不要放进state const AppContainer = createAppContainer(AppNavigator);
- 函数组件中直接使用JSX语法渲染顶层创建的导航容器即可
export default function App() { // 初始化逻辑、全局状态逻辑写在这里 return <AppContainer />; }
- 如果需要根据登录态、初始化状态切换不同导航栈,直接通过条件渲染分支切换即可,不要把对应导航容器存入state
// 两个导航容器都在顶层创建 const LoginContainer = createAppContainer(LoginStack); const MainContainer = createAppContainer(MainStack); export default function App() { const [isLoggedIn, setIsLoggedIn] = useState(false); return isLoggedIn ? <MainContainer /> : <LoginContainer />; }
注意:所有类组件都必须通过JSX语法渲染,不要直接加括号调用,否则必然抛出类不能作为函数调用的异常。
内容的提问来源于stack exchange,提问作者Adhithyan S
相关产品推荐
相关产品推荐

