TypeScript中带回调的函数参数类型不兼容问题求助
解决TypeScript回调参数类型不兼容问题
问题原因
你定义的CBTest类型要求回调函数必须能处理Param1 | Param2联合类型的任意值,但onExport1只接受Param1,onExport2只接受Param2,两者都不满足联合类型的处理要求,因此触发类型错误。
解决方案:用泛型关联场景与参数类型
通过泛型将场景标识(abc的取值)和回调参数类型绑定,让TypeScript能根据场景值精准推断回调应接收的参数类型,代码修改如下:
const onExport1 = ({ name1 }: { name1: string}) : void => { console.log(name1) } const onExport2 = ({ name2 }: { name2: string}) :void => { console.log(name2) } type Param1 = { name1: string } type Param2 = { name2: string } // 建立场景与参数类型的映射关系 type CaseMap = { case1: Param1, case2: Param2 } // 泛型函数关联场景和回调参数 const testExport = <T extends keyof CaseMap>(cb: (obj: CaseMap[T]) => void, abc: T) => { if (abc === 'case1') cb({ name1: "name1" } as CaseMap[T]) else cb({ name2: "name2" } as CaseMap[T]) } testExport(onExport1, "case1") // 类型匹配无误 testExport(onExport2, "case2") // 类型匹配无误
关键说明
CaseMap映射类型:明确场景字符串与对应参数类型的绑定关系,让TypeScript能通过场景值快速定位参数类型。- 泛型约束:用
T extends keyof CaseMap约束abc的取值范围,同时让回调参数类型自动匹配当前场景对应的CaseMap[T],确保回调参数与场景严格对齐。 - 类型断言:分支中用
as CaseMap[T]消除TypeScript对分支参数的类型歧义,确保类型推断准确。
如果觉得映射类型太繁琐,也可以用条件类型简化:
type CaseParam<T> = T extends 'case1' ? Param1 : Param2 const testExport = <T extends 'case1' | 'case2'>(cb: (obj: CaseParam<T>) => void, abc: T) => { if (abc === 'case1') cb({ name1: "name1" } as CaseParam<T>) else cb({ name2: "name2" } as CaseParam<T>) }
修改后,TypeScript会正确识别每个场景下的回调参数类型,彻底解决类型不兼容问题。
内容的提问来源于stack exchange,提问作者Trần Hồng
相关产品推荐
相关产品推荐

