2

What is <? super T> syntax?

I was reading this answer that cleared me some doubts but I didn't understand one thing in this line:

T extends Comparable< ? super T>

everyone in the replies of that post explained that T implements Comparable<T or T's superclass>; but there is written extends, so T is a subinterface of Comparable not a subclass so why would all the replies have implements as verb?

My only guess is that they all implied that T is an object whose static type is the subinterface of Comparable, but the dynamic type is actually an implementing class of comparable, is that so?

wattbatt
  • 447
  • 2
  • 13
  • 2
    A class can extend a class, and implement an interface. But when defining generic type bounds, we always use "extends" to mean "is this type or a subtype of this type". So, a subinterface or a class implementing the interface both qualify. See https://docs.oracle.com/javase/tutorial/java/generics/bounded.html: *Note that, in this context, extends is used in a general sense to mean either "extends" (as in classes) or "implements" (as in interfaces)* – JB Nizet Nov 24 '19 at 16:04
  • I'm sure there is a duplicate somewhere (I've seen a similar question not long ago), but I can't find it. – JB Nizet Nov 24 '19 at 16:07
  • Well think about it for a moment, will you ever get a `T` which isn't a concrete, instantiated object? It will always be a class, whether an anonymous implementation of an interface or a class which implements it. In terms of just simple references, there isn't a distinct `T implements XYZ` because from what I remember there wasn't much reason to make the distinction. – Rogue Nov 24 '19 at 16:41

2 Answers2

3

T can be either an interface type or a regular class type; either way, it "extends" the supertype.

The special keyword implements is only used when declaring a class and listing interfaces that it supports. (Even there, there's no real reason that Java needs to use a different keyword; we can easily imagine a parallel universe where a single extends clause is used to list zero or one superclass and zero or more superinterfaces, and Java sorts it out based on which listed classes are interfaces. But that decision was already set in stone long before generics and wildcards were introduced.)

ruakh
  • 175,680
  • 26
  • 273
  • 307
3

The truth is, T could be a class implementing Comparable, or a subinterface of Comparable. The word extends used in the generic constraint syntax does not mean the same thing as the word extends in a class inheritance clause.

The below code demonstrates both situations:

interface Foo {}
interface Bar extends Foo {}
class Baz implements Foo {}

public static <T extends Foo> void f(T t) {

}

Bar bar = new Bar() {};
f(bar); // compiles!
Baz baz = new Baz();
f(baz); // compiles!

However, T being a class implementing Comparable is a lot more likely than it being a subinterface of Comparable. The only subinterfaces of Comparable in the JDK are:

ChronoLocalDate, ChronoLocalDateTime<D>, Chronology, ChronoZonedDateTime<D>, Delayed, Name, Path, RunnableScheduledFuture<V>, ScheduledFuture<V>

None of which you would use very often, compared to classes that implements Comparable, such as Instant and String.

So people say "T is a class that implements Comparable" simply because it is the more likely situation.

Sweeper
  • 213,210
  • 22
  • 193
  • 313