类型脚本重载箭头函数

所以我们可以这样做:

export function myMethod (param: number) :number
export function myMethod (param: string) :string


export function myMethod (param: string | number): string | number {
if (typeof param === 'string') {
return param.toUpperCase()
} else {
return param + 1
}
}

我可以用箭头函数声明和实现它吗?

export var myMethodArror = (param: string): string
export var myMethodArror = (param: number): number


export var myMethodArror = (param: string | number): string | number => {
..
}

我知道复制变量声明是不可能的,但我的问题是: 是否有可能使用箭头符号使函数重载?

24013 次浏览

重载签名的声明始终是

function name(args...): result;

带有 function关键字和函数名。

你的语法

var myMethodArror = (param: string): string;

无效。它试图将类似于箭头函数开头的内容赋给一个变量,但该函数没有主体。你会得到错误

“ = >”意料之中

如果使用不同的签名重复此操作,那么还会得到一个重复的属性错误,或者可能是错误

后续的变量声明必须具有相同的类型。

这不是特定于箭头函数的。如果您尝试这样做,也会出现同样的问题

var myMethodArror = function(param: string): string;

这样就会产生

“{”预期

因为函数体不见了。

我猜它是在当时和现在之间添加的,因为您现在可以使用接口或类型(无关紧要,除了关键字之外语法相同)进行添加。当然也可以作为出口。但是函数必须被命名(我认为所有重载的函数都必须这样) ,所以如果你想用它作为回调函数,你必须首先声明它。

type IOverload = {
(param: number): number[];
(param: object): object[];
}


const overloadedArrowFunc: IOverload = (param: any) => {
return [param, param];
}


let val = overloadedArrowFunc(4);

我更喜欢这样,它减少了重复写作的需要。一遍又一遍地写这个名字很烦人。

另外,为了引出任何与此相关的问题,我已经在实现中将参数声明为 any。在当前状态下,这是允许编译的必要条件,而且,正如@ford04指出的那样,您将在函数内部失去类型安全性。当涉及到函数和它们的返回值时,似乎打印脚本仍然不能正确地处理标记的联合。或者,您可以有更严格的参数,但是您必须将返回值强制转换为任何。

此解决方案基于@Sam96,但保持箭头函数的代码完全类型化。

type Create = {
(): Vector<0>;
<T>(x: T): Vector<T>;
<T>(x: T, y: T): Vector<T>;
};


const create: Create = <T>(
x?: T,
y?: T
) => ({
x: x ?? 0,
y: y ?? x ?? 0,
});

可以使用交叉操作符 &进行重载。

export let myMethodArror = ((param: string | number): string | number => {
...
}) as ((param: string) => string) & ((param: number) => number)