You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

TypeScript中const unions作为不同签名回调注册表的类型问题

解决TypeScript联合函数类型调用的类型错误

问题分析

你这段代码里,registry[type].magic(...magicArgs)报错是因为TypeScript将Registry[T]["magic"]解析成了联合类型((d: number) => number) | ((d: string) => string)。调用联合类型的函数时,TypeScript要求参数必须满足所有分支的参数类型,也就是number & string(即never),所以出现类型不匹配的错误。

修复方案

这里给出两种可行的修复方式:

方案1:类型断言

直接将registry[type].magic断言为对应泛型T的具体函数类型:

const registry = {
  foo: {
    magic: (d: number) => d
  },
  bar: {
    magic: (d: string) => d
  }
} as const

type Registry = typeof registry

const registryMagic = <T extends keyof Registry>(type: T, magicArgs: Parameters<Registry[T]["magic"]>) => {
  // 断言为对应T的具体函数类型
  (registry[type].magic as (...args: Parameters<Registry[T]["magic"]>) => ReturnType<Registry[T]["magic"]>)(...magicArgs)
}

registryMagic("foo", [123])
registryMagic("bar", ["test"])

方案2:使用辅助函数关联类型

通过辅助函数强制TypeScript跟踪具体的类型分支,避免类型断言:

const registry = {
  foo: {
    magic: (d: number) => d
  },
  bar: {
    magic: (d: string) => d
  }
} as const

type Registry = typeof registry

const callMagic = <T extends keyof Registry>(entry: Registry[T], args: Parameters<Registry[T]["magic"]>) => {
  entry.magic(...args)
}

const registryMagic = <T extends keyof Registry>(type: T, magicArgs: Parameters<Registry[T]["magic"]>) => {
  callMagic(registry[type], magicArgs)
}

registryMagic("foo", [123])
registryMagic("bar", ["test"])

两种方式都能让TypeScript正确关联type参数和magicArgs的类型,消除错误。

内容的提问来源于stack exchange,提问作者lipp

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.01 19:03:10