java - 是否可以声明并实现一个方法一次,但改变返回类型以稳健地匹配子接口(interface)?

标签 java generics design-patterns polymorphism code-reuse

首先,我想说这没有任何用例。我唯一想做的就是探索这是否可能。

我想做的是将基接口(interface)中方法的返回签名“重新命名”为子接口(interface)的返回签名。

目标:声明并实现一个方法一次,但改变返回类型以匹配子接口(interface)。我已经弄清楚了在某些情况下如何实现这一目标,但在某些情况下它会失败。

想象一下,如果我有基本接口(interface) B 并且它有一个方法 B doWork()。另外,还有一个 B 的实现,它实现了 doWork()。由于 doWork() 的性质,该实现应该是唯一存在的实现。

现在,使用泛型可以很容易地做到这一点。对于上面的例子:

interface B<T extends B> {
    T doWork();
}

class BImpl<T extends B> implements B<T> {
    @Override
    public T doWork() { return something; }
}

子接口(interface)/impl 可能看起来像这样:

interface C extends B<C> {
    void somethingCSpecific();
}

class CImpl extends BImpl<C> implements C {
    @Override
    public void somethingCSpecific() {   }
}

任何构造 CImpl 的人都会看到 doWork() 返回一个 C。

C obj = new CImpl().doWork()  // The money shot.  No casting needed.

这就是它崩溃的地方......想象 B 现在看起来像这样:

public interface B<T extends B> {
    T thisOrThat(T that);
    boolean something();
}

我想在 BImpl 中执行此操作:

class BImpl<T extends B> implements B<T> {
    @Override
    public T thisOrThat(T that) {
        if (that.something())
            return that;
        return this;  //  Error!!  _this_ might be a different T than _that_.
    }
    @Override
    public boolean something()  { return whatever; }
}

注意错误发生的位置。

显然,如果没有不安全和可疑的 Actor 阵容,这就无法发挥作用。但如果我知道上面 thisOrThat 方法中 this 的实现与 that 的实现相同,那么一切都会好起来的。

所以,回答我的问题。有没有一种方法可以将 thisthat 限制为同一类型,而无需事先知道该类型?

或者也许有不同的方法来做到这一点,但有相同的结果?即只需声明并实现 thisOrThat() 一次,但返回类型可以适应子接口(interface)?

谢谢。

最佳答案

使您的类 BImpl 抽象化,并向其中添加一个 view 方法,该方法由扩展抽象基类的特定类实现:

public abstract class BImpl<T extends B<T>> implements B<T> {
   @Override
   public T thisOrThat(T that) {
       if (that.something())
           return that;
       return this.asT();
   }


    @Override
    public boolean something() {
        // TODO Auto-generated method stub
        return false;
    }

    protected abstract T asT();
}

然后你的每个类仍然需要实现T asT(),但这很简单并且编译时不会发出警告:

public class C extends BImpl<C> implements B<C> {
    @Override
    protected C asT() {
        return this;
    }
}

关于java - 是否可以声明并实现一个方法一次,但改变返回类型以稳健地匹配子接口(interface)?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/10218333/

相关文章:

java - Do While 循环第二次不与扫描仪协调

c# - 当我们有不同的返回类型时实现策略模式

java - 第二次加载后位图大小超出虚拟机预算

java - 如何为字段编写自定义注释,以便为该字段创建自定义 setter ?

java - 如何在 ListView Android 的页眉和页脚中使用 Butter Knife

c - 如何在通用排序函数中添加排序顺序选项

generics - 如何从 Dart/Flutter 中的泛型函数调用命名构造函数

c# - 我可以使用泛型方法作为一种模板模式吗?

c++ - 这个单例实现有问题吗?

scala - Akka Siblings 递归 ActorRef 要求