Description
Generics allow us to parameterize interfaces, classes, and methods in Java. Typically, generics are used in conjunction with containers. A container is a class used to hold objects in some meaningful way (e.g. an ordered list, a set).
Here is an example of a generic class:
class SomeClass<T> { private T someInstanceVariable; public SomeClass( T someVariable ) { someInstanceVariable = someVariable; } public T getSomeInstanceVariable() { return someInstanceVariable; } }
When creating a generic object, you may now specify the actual type of T:
SomeClass<String> someObject = new SomeClass<String>( "A String" );
Now every T in the class definition will be the specified parameter type. In the above example, T would be String. Typically, we would like to be able to do things with a generic type, but in the above example, we don't know anything about T, except that it will be an Object. So, we can call Object methods, like toString and equals. But what if we want to be more specific about the actual type of T?
We may "bound" a generic type to gurantee some associated behavior (available methods):
class SomeClass<T extends Comparable<T>> { private T someInstanceVariable; public SomeClass( T someVariable ) { someInstanceVariable = someVariable; } public T getSomeInstanceVariable() { return someInstanceVariable; } public boolean isLessThan( SomeClass<T> someArgument ) { if( someInstanceVariable.compareTo( someArgument ) < 0 ) return true; return false; } }
Now we have bounded type T to be a Comparable. Now in the isLessThan method, it is safe to assume that T has a compareTo method. Notice that even though Comparable is an interface, we use the "extends" keyword.
We may also define generic interfaces and generic methods. Generic interfaces follow the same pattern as the above class example, but generic methods look a little different:
public <U extends Comparable<U>> void someMethod( SomeClass<U> someArgument) // ...
You may also specify more than one generic type or bound a type by more than one interface:
class SomeClass<T extends Comparable<T>, S>
class SomeClass<T extends Comparable<T> & Iterable<T>>
In this lab, we will be creating our own generic class called CatalogItem, a Media interface, and two classes which implement the Media interface, CD and Book. CatalogItem will have two generic types bounded by the Comparable and Media interfaces, respectively. We will then use the ArrayList class to create Lists of CatalogItem objects and sort these Lists with a generic sort method for CatalogItems.
The details of the lab are as follows:
- We want to build a catalog of CDs with an Integer ID or key assigned to each CD (iPod) and a catalog of Books with a String ID or key assigned to each Book (Kindle), which we can then sort.
- As CatalogItem is a generic class with two parameters, we can create a CatalogItem with an Integer or String ID (or anything that is Comparable) along with a CD or Book object.
- A catalog will be represented as an ArrayList of CatalogItems. (Typically, we would make a special Catalog class. But for demonstration purposes, this has been simplified.)
- CatalogItem will have a Comparable parameter, but will also be comparable itself, allowing us to use a generic sort method to sort a List of CatalogItems.
- We will print the catalogs by utilizing List's toString to verify that the contents of our catalogs have indeed been sorted.