我可以在打字稿中强制执行函数的最后一个参数吗?

Ric*_*ler 5 typescript

假设我有一个函数类型接口,我想用它来强制执行特定函数的某个签名。

有没有办法强制函数的最后一个参数必须是特定类型?

有没有办法做这样的事情:

interface SomeType { /*...*/ }

/**
 * this is the function type I want to enforce
 * I want the last argument of any `Modifcation` to be `SomeType`
 */
interface Modification {
    (...args: [...firstArgs: any[], lastArgument: SomeType]): void
}

// enforcing `Modification`
const someModification: Modification = (firstParam: string, second: number, third: SomeType) => {
    /*...*/
}
Run Code Online (Sandbox Code Playgroud)

我知道打字稿使用传播语法元组类型,但上面的伪代码不起作用。

有没有办法做到这一点?


编辑:

免责声明:我认为没有办法做我想做的事情,因此这个问题可能不完全具有建设性。

语境:

我有一组类,我想对这些类的特定方法强制执行某种约定。我可以通过声明另一个接口并说明我的类实现该接口来强制某个方法必须符合一个函数类型

例如

interface Convention {(arg0: string, arg1: number): Something}

interface MyClassMethodRequirements {
    myMethod: Convention,
    myOtherMethod: Convention
}

class MyClass implements MyClassMethodRequirements {
    myMethod(a: string, b: number) { return new Something(); }
    myOtherMethod(label: string, aNumber: number) { return new Something(); }
    otherMethod() { return 'just another non-conforming method' }
}
Run Code Online (Sandbox Code Playgroud)

我想要达到的目标:

Convention以上仅仅是一个例子。我要强制执行的是,断言为Convention必须具有/考虑两个参数的方法。

例如(伪代码)

interface NewConvention {(firstArg: any, lastArg?: RequiredType): Something}

interface MyClassMethodRequirements {
    myMethod: NewConvention,
    myOtherMethod: NewConvention
}

class MyClass implements MyClassMethodRequirements {
    myMethod(a: string, b?: RequiredType) { return new Something(); }
    // i want an error here because `myOtherMethod` doesn't list `lastArg: RequiredType` in it's parameters
    myOtherMethod(label: string) { return new Something(); }
    otherMethod() { return 'just another non-conforming method' }
}
Run Code Online (Sandbox Code Playgroud)

对于更多的上下文,lastArgofNewConvention假设是一个可选的覆盖。

同样,我不认为我想要实现的目标是可能的,所以这可能没有建设性。

谢谢你的帮助 :)

Nit*_*mer 1

您可以将第一个参数(类型为SomeType)作为可选参数,如下所示:

interface SomeType {
    a: number; // just so it's not an empty definition
}

type Modification =
    { (first: SomeType, ...rest: (string | number)[]): void; }
    | { (...rest: (string | number)[]): void; }

// fine
const someModification1: Modification = (firstParam: string, second: number) => {}
const someModification2: Modification = (third: SomeType, firstParam: string, second: number) => { }

// error
const someModification3: Modification = (firstParam: string, second: number, third: SomeType) => { }
Run Code Online (Sandbox Code Playgroud)

请注意,如果您使用any[]args,那么它也会覆盖SomeTypearg。