TypeScript中如何无需显式传泛型让扩展类型适配事件监听?
解决方案:用泛型类实现类型安全的简化调用
可以通过将抽象类DomainEvent改为泛型类(采用奇异递归模板模式),实现无需显式指定泛型参数即可适配子类事件的handler,同时保证类型安全。
具体实现步骤:
修改抽象类定义
引入泛型参数T,并绑定到自身的子类类型:import java.util.function.Consumer; abstract class DomainEvent<T extends DomainEvent<T>> { public void on(Consumer<T> handler) { // 此处转换安全,因子类会正确将T指定为自身类型 handler.accept((T) this); } }子类继承时指定自身为泛型参数
子类继承DomainEvent时,将泛型参数T设为子类自身:class UserDomainEvent extends DomainEvent<UserDomainEvent> { // 子类业务逻辑示例 private String userId; public UserDomainEvent(String userId) { this.userId = userId; } public String getUserId() { return userId; } }简化调用
调用时无需任何泛型声明,编译器会自动识别handler的参数类型为UserDomainEvent:public class Main { public static void main(String[] args) { UserDomainEvent userEvent = new UserDomainEvent("12345"); // handler参数e自动推导为UserDomainEvent类型 userEvent.on(e -> { System.out.println("处理用户事件,用户ID:" + e.getUserId()); }); } }
为什么原方案会报错?
原on1方法的参数是Consumer<DomainEvent>,而你传入的是Consumer<UserDomainEvent>——这两个类型不兼容:
Consumer<DomainEvent>可以处理所有DomainEvent的子类实例;Consumer<UserDomainEvent>只能处理UserDomainEvent实例。
编译器为了避免类型不安全的情况(比如on1内部给handler传入其他子类实例),会直接报错。
原on2的泛型方法虽然可行,但通过泛型类的方式,调用时更简洁,无需依赖方法级泛型的自动推断,代码结构也更清晰。
内容的提问来源于stack exchange,提问作者ZiiMakc
相关产品推荐
相关产品推荐

