Java:在子类型中指定泛型类型限制

标签 java generics subtyping

我有一个关于 Java 泛型类型的问题。具体来说,目前我有一些类似这样的代码:

public interface Foo {
   public <T> void bar(T[] list)
}

public class FooImpl implements Foo{
   @Override
   public <T extends Comparable<? super T>> void bar(T[] list) {
       ...
   }
}

问题是,编译器现在提示我没有在我的 FooImpl 类中实现 bar 方法。

我想要的是对泛型类型进行一些额外的限制,特别是它们应该是可比较的。但我不想在我的 Foo 接口(interface)中施加该限制,因为所有实现都不需要该限制。 这可能吗?我应该如何解决?

提前致谢!

编辑 1:修复错别字类 --> 类和接口(interface) --> 接口(interface)。但是返回类型仍然是 void,而不是 T,我想这是无关紧要的。我的实际返回类型是 boolean 值。

编辑 2:实际代码,按要求:

public interface SortedCriteria {

    public <E> boolean isSorted(E[] list);

}

public class AscendingCriteria implements SortedCriteria {

    @Override
    public <E extends Comparable<? super E>> boolean isSorted(E[] list) {
        int length = list.length;
        for (int i = 1; i < length; i++) {
            if (list[i].compareTo(list[i-1]) < 0) return false;
        }
        return true;
    }

}

最佳答案

你想做的事情被拒绝了,因为它会彻底破坏多态性。具有 Foo 实例的调用者可以具有您的子类的实例或任何其他子类的实例。并且由于接口(interface)保证可以使用任何类型的数组作为参数来调用该方法,因此您的子类不能通过限制它接受的数组类型来破坏此契约(除非它在运行时通过检查数组的类型来做到这一点)当然是通过抛出异常)。

这归结为 Liskov 替换原则,它是多态和 OO 的基础。

但也许您真正想要的是使 Foo 成为通用类型:

public interface Foo<T> {
    public void bar(T[] list);
}

public class FooImpl<T extends Comparable<? super T>> implements Foo<T> {
   @Override
   public void bar(T[] list) {
       ...
   }
}

关于Java:在子类型中指定泛型类型限制,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21658622/

相关文章:

java - 我应该如何在 Java 中实现 Message 类的子类型?

java - "? extends E"和 "T extends E"有什么区别?

java - AWS SQS 和 SES 依赖库相互影响

java - LibGdx 工具错误

swift - 我可以使一个结构或类多次符合通用协议(protocol)吗?

java - 通用列表<>层次结构困惑

scala - @uncheckedVariance 在 Kotlin 中?

java - 如何自行部署 Spring Boot 应用程序

java - 用于检查 BlackBerry 设备是否受密码保护的 API

c# - 是否可以创建一个通用的 Func<T><T>