如何在Java中使用有界通配符?

时间:2017-03-14 22:53:09

标签: java types covariance contravariance

wikipedia article about co- and contravariance中有一个示例用例,然后是一个描述类型声明含义的解释性句子。我发现这非常有用。在阅读了几次解释后,我觉得我理解它的内容。

<T extends Comparable<? super T>> T max(Collection<T> coll);
  

有界通配符? super T传达max仅从Comparable接口调用逆变方法的信息。

有人可以用类似的语言解释andThen() java.util.function.Consumer@FunctionalInterface函数的类型声明是什么意思:

public interface Consumer<T> {
    void accept(T t);
    default Consumer<T> andThen(Consumer<? super T> after) {

e.g。

  

有界通配符? super T传达andThen ....?

的信息

我还有一个次要问题:我怎样才能发现自己,这种类型声明的含义是什么?例如。在上面的第一个例子中,来自java.util.Collections util类:类的类型边界如何 - 能够传达关于T的方法正在做什么的信息?任何人都能指出我在Java语言规范中的相关段落吗?

1 个答案:

答案 0 :(得分:0)

第一个问题的可能答案:

public interface Consumer<T> {
    void accept(T t);
    default Consumer<T> andThen(Consumer<? super T> after) {
  

有界通配符? super T传达andThen消费者T或超T类别的信息。 contravariant 消费者,作为论据。

第二个问题的可能答案:https://stackoverflow.com/a/2501513

基本上 - 完全独立于Java语言中的泛型(!) - method return return types are inherently "covariant"(假设为“生成者”)。如果覆盖子类中的方法,则始终可以声明更具体的返回类型。

方法参数当然也是“协变” - 您只能传递比方法签名指定的更具体的对象。但是在子类上,尽管该方法在技术上not overriden for non-parametric arguments - 坚持Liskov_substitution_principle - 在子类中声明“逆变”参数类型通常是有意义的 - 如果名称和其他参数相等 - “重载”父类中的方法。然后,“静态”(引用类型管理)方法分派将确保(不太具体的)子方法被称为wins。假设方法参数被“消耗”,然后应用PECS。无论如何,对于通用参数,bridge methods are generated并且它有点毛茸茸。但我们会get there