I'm new to generics (and Java, and Stack Overflow), and there is a point in the textbook I'm learning from where it discusses the implementation of a generic binary search tree (excerpt below).
The Comparable interface is generic, so let’s consider storing the following type of elements in our search tree:
< T extends Comparable< T>>
This still causes a problem. Suppose that both Dog and Cat are subclasses of a class Mammal and that the Mammal class implements the Comparable interface. Now if we create a binary search tree that stores Mammal objects, then a Dog and Cat could be added, but are not really comparable to each other. So this solution, if used in this particular way, has the same problem as using the nongeneric version of Comparable. A more comprehensive solution, though not as intellectually satisfying, is to write the generic type as:
< T extends Comparable< ? super T>>
This declaration restricts the comparable nature of the element to any superclass of T.
So I get why the type parameter needs to be Comparable< T>, but then the book claims that this can pose problems if the tree of Mammals contains different subtypes that attempt to invoke the compareTo() method on each other. Well if the reference type for the Cat and Dog objects in the tree is Mammal, then wouldn't they be invoking Mammal's compareTo() method anyway (being Comparable< Mammal>), making it a valid comparison (just on the Mammal level)?
I don't understand what difference Comparable< ? super T> makes, because would that not be the same thing, except perhaps if Mammals aren't Comparable then it falls back to a Comparable superclass like the Animal class or something?
I'm probably missing something, like some nasty consquence of type erasure or something that will cause the comparisons to not work like I'm thinking they would.