我试图创建一个通用的 Package 器函数,它将 Package 传递给它的任何函数。
最基本的 Package 器函数看起来类似于
function wrap<T extends Function>(fn: T) {
return (...args) => {
return fn(...args)
};
}
我试着用它像:
function foo(a: string, b: number): [string, number] {
return [a, b];
}
const wrappedFoo = wrap(foo);
现在wrappedFoo
正在获取(...args: any[]) => any
类型
有没有可能让wrappedFoo
模仿它所 Package 的函数的类型?
6条答案
按热度按时间cunj1qz11#
这适用于任意数量的参数,并保留所有参数和返回类型
yacmzcpb2#
最近需要用箭头函数来做这个,提出了一种比其他答案更容易的方法,并解决了spread运算符和
Symbol.iterator
的问题(在ts 3. 8中测试过)AnyFunction
,这样我们就可以使用rest运算符并取出参数类型/返回类型Func extends AnyFunc
可以描述我们特别喜欢的任何函数的类型Func
,则会出现无法使用不同的子类型示例化 Package 函数的问题,因此我们需要重新构造它Parameters<Func>
将任意参数作为元组获取Symbol.iterator
问题的解决方法是使用...Array.from(args)
而不是...args
ReturnType<Func>
获取任意返回类型Package 后的函数现在将具有与内部函数相同的签名,几乎可以执行任何操作
1tu0hz3e3#
通过做两个更改,可以创建一个 Package 器函数,该函数接受并返回与其 Package 的函数相同的类型
1.将 Package 函数的返回值指定为要 Package 的
T
泛型1.将返回的函数强制转换为
<any>
例如:
那么
const wrappedFoo = wrap(foo);
的类型则正确地为:
sc4hvdpw4#
这是可能的,但是如果您希望能够传递不同类型和数量的参数,则可能会有点混乱。
你的例子可以这样做:
则类型为:
是
(a: string, b: number) => [string, number]
。(code在Playground)
但是正如您所看到的,如果您希望能够使用不同的签名,那么使用这种方法并不方便(例如,我的示例只适用于两个参数)。
你能做的就是只传递一个由接口支持的参数:
(code在Playground)
在我看来,这将更容易处理。
nmpmafwu5#
您可以使用重载为 Package 具有0、1、2、3、4个或更多参数的函数提供特定类型。如果您的某个函数需要更多参数,请添加额外的重载或让它回退到其余参数的情况。
它不是很漂亮,但它给予了最准确的类型。
8mmmxcuj6#
如果您希望执行类似于用逻辑/条件 Package 异步函数操作: