CSCE 314 Lecture 28
Jump to navigation
Jump to search
« previous | Monday, November 7, 2011 | next »
Java Basics
Typesafe polymorphic containers:
Every class extends the base/root Object class.
Generics
Allow us to parameterize types for classes and methods (type parameterization is almost identical to templates in C++)
C++ rewrites code filling in the parameters, but Java compiler maintains each parameter as an Object type and casts variables to specified types.
Without Generics/Templates
List l = new LinkedList()
l.add(new Integer(0));
Integer x = (Integer) l.iterator().next();
String s = (String) l.iterator().next(); // bad cast exception
With Generics/Templates
List<Integer> l = new LinkedList<Integer>()
l.add(new Integer(0));
Integer x = l.iterator().next();
String s = l.iterator().next(); // compile time error
Parameterized Method Example
public class ArrayUtil
{
// ...
public static <E> void print(E[] a)
{
for (E e : a) System.out.print(e.toString() + " ");
System.out.println();
}
}
Rectangle[] rects = // ...
String[] strs = // ...
// can be used either way
ArrayUtil.<Rectangle>print(rects);
ArrayUtil.print(strs);
Notice that there is a toString method assumed on all Objects. In Haskell, we had to explicitly state that a has to be of type class Show:
print :: [a] -> IO ()
print ls = sequence (map (putStr . show) ls) >> return () -- ERROR!
print :: Show a => [a] -> IO ()
print ls = sequence (map (putStr . show) ls) >> return () -- This is OK
Bounds on Generics
Provides constraints on types that can be used in generic templates:
class SortedClass<T extends Comparable & Serializable> { /* ... */ } !a!D
Wildcards
static void printAll(List<?> l) {
for (Object o : l) System.out.println(o);
}