当前位置: 首页 > 知识库问答 >
问题:

使用Java泛型重构方法

戚锦
2023-03-14

我有以下两种方法:

public void doStuffA(String str, List<ClassA> list){
    list.stream()
            .filter(s -> s.getObjValue().equalsIgnoreCase(str))
            .findFirst()
            .ifPresent( obj ->{
                throw new RuntimeException();
            });
}

public void doStuffB(String str, List<ClassB> list){
    list.stream()
            .filter(s -> s.getObjValue().equalsIgnoreCase(str))
            .collect(Collectors.toList())
            .findFirst()
            .ifPresent( obj ->{
                throw new RuntimeException();
            });
}

ClassA和ClassB都有相同的方法getObjValue,但它们没有关系。它们不从公共类或接口继承。由于这些方法几乎是相同的,我是否可以使用泛型来使用一个签名如下的方法来消除这段代码的重复:

public void doStuffB(String str, List<?> list)

共有1个答案

郑翰海
2023-03-14

如果类A和类B不共享声明String getObjValue()的公共接口或超类,则不可能完全消除重复。

我假设可以安全地删除doStuffB()的第3行(阻止示例代码编译的.collect(Collectors.toList())),这样doStuffA()doStuffB()就可以做同样的事情。

然后,您可以通过分解流处理并使用谓词来减少大量的重复:

public void doStuffA(String str, List<ClassA> list) {
    doStuff(str, list, s -> s.getObjValue().equalsIgnoreCase(str));
}

public void doStuffB(String str, List<ClassB> list) {
    doStuff(str, list, s -> s.getObjValue().equalsIgnoreCase(str));
}

private <T> void doStuff(String str, List<T> list, Predicate<? super T> predicate) {
    list.stream()
        .filter(predicate)
        .findFirst()
        .ifPresent( obj -> {
            throw new RuntimeException();
        });
}
 类似资料:
  • 安吉丽卡·兰格(Angelica Langer)在关于仿制药的常见问题解答中说(参见Technicalities.FAQ822): 如果这些方法具有具有不同边界的类型参数,则它们不会重写,因为这些方法的签名不是重写等价的。请记住,类型参数边界是泛型方法签名的一部分。 示例(泛型子类型方法重载泛型超类型方法;不推荐): 我不明白为什么方法在类中重载。据我所知,这应该是一个编译时错误,因为在和中具有相

  • 我正在尝试覆盖子类中从父类继承抽象方法的方法。我正在尝试更改泛型返回类型,但我有点困惑。 基本泛型类: 儿童班: 实施: 我想在其中覆盖参数化方法的子视图类: 这是Eclipse抛出错误消息的地方: 注意类和接口:事件和级别: 以及继承自 的 Model 类 我试图实现的是编写更抽象的代码,因为这些类、接口将被多个类扩展(在我的例子中是不同的视图类型)。这些是抽象类:< code>BaseAdap

  • 来自Java文档:在类C中声明的实例方法m1覆盖在类A中声明的另一个实例方法m2,如果以下所有条件都为真:。。。。。m1的签名是m2签名的子签名(§8.4.2)。 方法m1的签名是方法m2签名的子签名,前提是:m1的签名与m2签名的擦除相同(§4.6)。 是对一个 如果是这样,什么是错的? EDIT1:或者如果我切换通用类型: 这种情况下有什么问题? EDIT2:我知道如何修复它,但我想了解,在这

  • 这是如何编译的: 但这并不是: 它给我以下编译错误: Impl不是抽象的,并且不会覆盖测试中的抽象方法getValue(整数) 错误:名称冲突:Impl中的getValue(T)和测试中的getValue(Integer)具有相同的擦除,但两者都不重写另一个 擦除不能确保t被整数替换吗?那么为什么第二个例子是无效的呢?

  • 我正在做一个体验,尝试用以下方式重写泛型类的方法: 为什么我不能?编译错误是 yGenFun。java:15:错误:对doX的引用不明确,Do中的方法doX(A)和MyGenFun中的方法doX(T)都匹配x.doX(“测试”);^其中A、T是类型变量:在类Do T中声明的extends对象扩展在类MyGenFun 1 error中声明的CharSequence 如果我注释“第1行”,我可以编译代

  • 我试图覆盖add(),但它不会编译 错误消息 java:36:错误:名称冲突:AVLTree中的add(E#1)和BinaryTree中的add(E#2)具有相同的擦除,但两者都不重写另一个公共void add(E toInsert)^,其中E#1、E#2是类型变量:E#1扩展了在类AVLTree中声明的Comparable E#2扩展了在类BinaryTree中声明的Comparable