这是一个解释我要问什么的例子!
// Given an events definition
interface IEventDef {
event1: () => void,
event2: (data: T) => void
// ...
}
它如何声明如下内容:
public on(
eventName: keyof IEventsDefinitions, // get the literal string here (when it's used)
callback: IEventsDefinitions[EventName] // and use it on the next param type ???
) {
}
关键是如何做出这样的定义,以便我们在编写时:
obj.on('event1', (data) => {
// need data to be correctly infered and that using the string literal 'event1'! Technically that is possible to be done
// as it is, it doesn't inference
})
// 需要正确推断数据并使用字符串文字“event1”!技术上可以做到
实际上,它不会进行推理!
也知道这样的解决方法有效:
public on<EventName extends keyof IEventsDefinitions>(
eventName: keyof IEventsDefinitions,
callback: IEventsDefinitions[EventName]
) {
并像这样使用它:
on<"event1">('event1', (data) => {})
数据将被正确推断!但是很丑! (技术上可以从字面推断)!
所以我在问我们怎么能以任何方式做到这一点!?提前谢谢你!
答案 0 :(得分:3)
您的解决方法版本大部分是正确的,您缺少的部分是 eventName
和 callback
参数需要引用 相同 键。
您需要 eventName: keyof IEventsDefinitions
而不是 eventName: EventName
,其中 eventName
参数的值与函数的通用变量匹配。
function on<EventName extends keyof IEventsDefinitions>(
eventName: EventName,
callback: IEventsDefinitions[EventName]
) {
您不再需要在调用函数时指定泛型,因为现在 typescript 能够从第一个参数推断泛型。
on('event1', () => {})
on('event2', (data) => {})