所以使用@next版本的Typescript
可以很好地工作function fork<
Paths extends Partial<Paths>,
OutputType extends keyof Paths
> (callback: () => OutputType, paths: Paths) {
const result = callback()
const path: () => ReturnType<Paths[OutputType]> = paths[result]
const pathResult = path()
return pathResult
}
const myResult = fork(() => 'bar', {
foo: () => 'bip',
bar: () => 123
})
根据返回的第一个回调字符串, myResult 输入正确。
然而,当我做这个小小的改变时:
function fork<
Paths extends Partial<Paths>,
OutputType extends keyof Paths
> (callback: () => OutputType, paths: Paths) {
const result = callback()
const path: (p: string) => ReturnType<Paths[OutputType]> = paths[result]
const pathResult = path('foo')
return pathResult
}
const bah = fork(() => 'bar', {
foo: (p) => 'bip',
bar: (p) => 123
})
基本上只是添加一个参数,整个事情就没有好的错误信息。
要看这个,只需使用最新的2.8(@next)版本的Typescript将代码粘贴到VS Code中。
答案 0 :(得分:2)
我认为你可能会在&#34;隐含any
&#34;中遇到一些怪癖。键入函数参数。我几乎总是使用--noImplicitAny
编译器选项,当我在这里为参数提供显式类型注释时,你的错误似乎消失了:
const bah = fork(() => 'bar', {
foo: (p: any) => 'bip',
bar: (p: any) => 123
})
话虽如此,您使用的类型参数限制是奇怪的。我不知道Paths extends Partial<Paths>
应该达到的目标。就个人而言,我倾向于像这样输入你的功能:
function fork<T, K extends keyof T>(
callback: () => K,
paths: {[P in keyof T]: (p: string)=>T[P]}
): T[K] {
const result = callback()
const path = paths[result];
const pathResult = path('foo')
return pathResult
}
使用inference from mapped types代替predefined conditional type ReturnType<>
。使用条件类型并没有什么问题,但由于它们没有正式可用,我不知道它是否足够稳定可以使用。但无论如何,您应该以一种让TypeScript知道它们应该具有属性的方式来定义paths
的类型。
希望这很有用。祝好运!