What is the difference between and ?

The first allows process of a List<Integer>, a List<Double>, etc. The second doesn’t.

Generics in Java are invariant. They’re not covariant like arrays.

That is, in Java, Double[] is a subtype of Number[], but a List<Double> is NOT a subtype of List<Number>. A List<Double>, however, is a List<? extends Number>.

There are good reasons for generics being invariant, but that’s also why the extends and super type are often necessary for subtyping flexibility.

See also

  • Java Tutorials/Generics/Subtyping
    • Explains why generics invariance is a good thing
  • More fun with wildcards
    • Explains some uses of super and extends for bounded wildcards
  • Java Generics: What is PECS?
    • This discusses the “Producer extends Consumer super” principle
    • Effective Java 2nd Edition, Item 28: Use bounded wildcards to increase API flexibility

Leave a Comment