类型 '( items : PropsWithChildren<TodoProps>) => Element[]' 不可分配给类型 'FunctionComponent<Tod
Posted
技术标签:
【中文标题】类型 \'( items : PropsWithChildren<TodoProps>) => Element[]\' 不可分配给类型 \'FunctionComponent<TodoProps>\'【英文标题】:Type '( items : PropsWithChildren<TodoProps>) => Element[]' is not assignable to type 'FunctionComponent<TodoProps>'类型 '( items : PropsWithChildren<TodoProps>) => Element[]' 不可分配给类型 'FunctionComponent<TodoProps>' 【发布时间】:2020-03-12 20:36:06 【问题描述】:我正在学习 Typescript-react,但我陷入了这个错误 Type '( items : PropsWithChildren<TodoProps>) => Element[]' is not assignable to type 'FunctionComponent<TodoProps>'
,我对此迷失了。
完全错误:
Type '( items : PropsWithChildren<TodoProps>) => Element[]' is not assignable to type 'FunctionComponent<TodoProps>'.
Type 'Element[]' is missing the following properties from type 'ReactElement<any, string | ((props: any) => ReactElement<any, string | ... | (new (props: any) => Component<any, any, any>)> | null) | (new (props: any) => Component<any, any, any>)>': type, props, key
代码链接:sandbox repo。
在TodoList.tsx
文件中声明TodoList
函数时发生错误。
感谢任何帮助。干杯!
代码:
import React from "react";
interface Todo
id: number;
content: string;
completed: boolean;
interface TodoProps
items: Todo[];
// v------v here is error
const TodoList: React.FC<TodoProps> = ( items ) =>
return items.map((item: Todo) => <div key=item.id>item.id</div>);
;
export default TodoList;
【问题讨论】:
【参考方案1】:是的,这个错误可能听起来有点令人困惑 - 本质上它表示您只能在函数组件定义中返回单个 ReactElement
或其等效的 JSX.Element
,由 React.FC
类型强制执行。
React Fragmentssolve这个限制,所以可以写TodoList
in the following manner:
interface TodoProps
items: Todo[];
const TodoList: React.FC<TodoProps> = ( items ) => (
<React.Fragment>
items.map((item: Todo) => (
<div key=item.id>item.id</div>
))
</React.Fragment>
);
简写:
const TodoList: React.FC<TodoProps> = ( items ) => (
<>
items.map(( id ) => <div key=id>id</div>)
</>
);
顺便说一句:使用纯JS,类和函数组件都可以返回 multiple elements in an array作为渲染输出。目前,TS 有一个type incompatibility 用于函数组件中的返回数组,因此 Fragments 在这里提供了一个可行的解决方法(除了type assertions)。
【讨论】:
这就是我讨厌TS的原因 听起来我与 ol' JS Date API 的关系(; 。让我们保持积极态度,等待#21699 的修复(这也解释了上述行为的历史原因)【参考方案2】:我遇到了类似的错误。最终,我注意到在使用 TypeScript 将组件转换为 FunctionComponent 时,我错误地将文件从 .js 重命名为 .ts 而不是 .tsx。
【讨论】:
【参考方案3】:当我尝试从我的 Loading
组件返回 children
道具时,我也遇到了这个错误,如下所示。
const loading, children = props;
return loading ? <p>Loading ... </p> : children;
然后我意识到 React 只期望其 render
方法的一个返回值(1 个父组件)。因此我用 React.Fragment
包装了 children 道具由<></>
表示,这解决了我的问题。下面是我的Loading
component 示例,希望对其他人有所帮助。
import FunctionComponent from "react";
interface ILoadingProps
loading: boolean;
export const Loading: FunctionComponent<ILoadingProps> = (props) =>
const loading, children = props;
return loading ? <p>Loading ... </p> : <>children</>;
;
【讨论】:
以上是关于类型 '( items : PropsWithChildren<TodoProps>) => Element[]' 不可分配给类型 'FunctionComponent<Tod的主要内容,如果未能解决你的问题,请参考以下文章
“String”类型不是 Flutter 中“Item”类型的子类型
Java 泛型编译错误:不兼容的类型:Item#1 无法转换为 Item#2