是否可以标记特定方法模式以返回特定类型?
Posted
技术标签:
【中文标题】是否可以标记特定方法模式以返回特定类型?【英文标题】:Is is possible to mark specific methods paterns to return a specific type? 【发布时间】:2022-01-22 21:31:25 【问题描述】:是否可以在 typescript 中定义一个仅应用于以某个单词开头并导致它们具有某种返回类型的方法的接口?我想到了类似的东西:
interface IPattern
[k: 'handle' + string]?: () => SomeClass
这样实现 IPatten 并具有以句柄开头的方法的类将被强制返回 SomeClass 对象,而其他方法则不会,例如:
class ForcedClass implements IPattern
foo(): number; // ok
handleFoo(): SomeClass; // ok
handleBar(): number; // error
我知道可以将抽象类与我需要的所有方法一起使用,但是由于handle + something
的组合用于许多不同的实现,因此为每个实现创建一个抽象会很冗长;
【问题讨论】:
【参考方案1】:您可以非常接近索引签名和模板文字类型:
interface IPattern
[k: `handle$string`]: () => SomeClass
class ForcedClass implements IPattern
[k: `handle$string`]: () => SomeClass
foo(): number return 0 // ok
handleFoo(): SomeClass return "0 " ; // ok
handleBar(): number return 0 // error
new ForcedClass()['handleBaz'](); // this is ok, because of the index signature
new ForcedClass().handleBaz(); // this is ok, because of the index signature
Playground Link
索引方法的问题在于,虽然类成员是针对它进行验证的,但这也意味着您可以使用符合 handle$string
模板文字类型的任何值进行索引,即使该成员实际上不是班级。
另一种选择是使用类型来验证类的实际键,而不添加索引签名:
type IPattern<T> = Record<Extract<keyof T, `handle$string`>, () => SomeClass>
class ForcedClass implements IPattern<ForcedClass>
foo(): number return 0 // ok
handleFoo(): SomeClass return "0 " ; // ok
handleBar(): number return 0 // error
new ForcedClass().handleBaz(); //error
new ForcedClass().handleFoo(); //ok
Playground Link
【讨论】:
感谢您的回答,我会关注有关索引签名的文档,顺便问一下,这些实现是否也适用于继承,或者每个子类都必须自己实现该模式?跨度> @LeoLetto 不幸的是,子类也需要自己实现这一点 好吧,我确实试过了,第一种方法是用抽象模式的子类来做的……第二种方法虽然看起来更优雅也不起作用,在这一点上我会留下来第一个,因为我可以抽象它以避免在每个子类中实现以上是关于是否可以标记特定方法模式以返回特定类型?的主要内容,如果未能解决你的问题,请参考以下文章