我试图在Typescript中使用泛型,以便将泛型参数用作索引来调用存储在对象中的函数。
我收到的错误是:
[ts]无法调用类型缺少调用签名的表达式。类型'((变量:{insertId:number;})=>字符串)| ((变量:{updateId:数字;值:字符串;})=>字符串)| ((variable:{deleteId:number;})=>字符串)'没有兼容的呼叫签名。[2349]
要么
类型'QueryInput [T]'的参数不能分配给类型'{insertId:number; }&{updateId:number; 值:字符串;}&{deleteId:number; }'。输入'{insertId:number; } | {updateId:number; 值:字符串;} | {deleteId:数字;}'不能分配给类型'{insertId:number; }&{updateId:number; 值:字符串;}&{deleteId:number; }'。输入'{insertId:number; }'不能分配给类型'{insertId:number; }&{updateId:number; 值:字符串;}&{deleteId:number; }'。输入'{insertId:number; }”缺少类型“ {updateId:number; 值:字符串;}':updateId,值类型'QueryInput [T]'不能分配给类型'{insertId:number; }'。输入'{insertId:number; } | {updateId:number; 值:字符串;} | {deleteId:数字;}'不能分配给类型'{insertId:number; }'。类型'{updateId:number;缺少属性'insertId'。值:字符串;}”,但类型为“ {insertId:number; }'。ts(2345)App.tsx(7,13):此处声明为'insertId'。(参数)变量:QueryInput [T]
这是一个复制该问题的示例代码:
type Query = "insert" | "update" | "delete";
interface QueryInput {
insert: { insertId: number };
update: { updateId: number; value: string };
delete: { deleteId: number };
}
type QueryObject = { [T in Query]: (variable: QueryInput[T]) => string };
const queries: QueryObject = {
insert: variable => "insert",
update: ({ updateId, value }) => "update",
delete: variable => "delete"
};
const getQuery = <T extends Query>(query: T, variables: QueryInput[T]) => {
return queries[query](variables); // this line throws an error
}
看来Typescript引擎无法解析函数的正确签名-尽管肯定只有1个可能的签名(从返回的那个queries[query]
)。
似乎query
和variables
已正确解决,并具有适当的类型。
如果您想要快速的肮脏解决方案进行编译,
const getQuery = <T extends Query>(query: T, variables: QueryInput[T]) => {
let v: any = variables;
return queries[query](v); // this line doesnt throw an error
}
这不是理想的方法,但是无论如何getQuery本身似乎都不需要更改。而且,对于此解决方案,仍将按您希望的方式键入getQuery的用法,而无需输入实现。
直到找到更好的解决方案。
本文收集自互联网,转载请注明来源。
如有侵权,请联系[email protected] 删除。
我来说两句