0% found this document useful (0 votes)
4 views24 pages

3 Java Generics Subtyping

The document discusses Java generics and subtyping, highlighting that while arrays are covariant, generic classes are not, such as LinkedList<String> not being compatible with LinkedList<Object>. It introduces the concept of wildcards and bounded wildcards to handle generics more effectively. The summary emphasizes the use of type quantification and wildcards to avoid type errors and enhance flexibility in generic programming.

Uploaded by

upsvivo
Copyright
© All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
4 views24 pages

3 Java Generics Subtyping

The document discusses Java generics and subtyping, highlighting that while arrays are covariant, generic classes are not, such as LinkedList<String> not being compatible with LinkedList<Object>. It introduces the concept of wildcards and bounded wildcards to handle generics more effectively. The summary emphasizes the use of type quantification and wildcards to avoid type errors and enhance flexibility in generic programming.

Uploaded by

upsvivo
Copyright
© All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd

Java generics and subtyping

Madhavan Mukund
[Link]

Programming Concepts using Java


Week 5
Extending subtyping in contexts
If S is compatible with T, S[] is compatible with T[]
ETicket[] elecarr = new ETicket[10];
Ticket[] ticketarr = elecarr;
// OK. ETicket[] is a subtype of Ticket[]

Madhavan Mukund Java generics and subtyping Programming Concepts using Java 2/9
Extending subtyping in contexts
If S is compatible with T, S[] is compatible with T[]
ETicket[] elecarr = new ETicket[10];
Ticket[] ticketarr = elecarr;
// OK. ETicket[] is a subtype of Ticket[]

But . . .
...
ticketarr[5] = new Ticket();
// Not OK. ticketarr[5] refers to an ETicket!

Madhavan Mukund Java generics and subtyping Programming Concepts using Java 2/9
Extending subtyping in contexts
If S is compatible with T, S[] is compatible with T[]
ETicket[] elecarr = new ETicket[10];
Ticket[] ticketarr = elecarr;
// OK. ETicket[] is a subtype of Ticket[]

But . . .
...
ticketarr[5] = new Ticket();
// Not OK. ticketarr[5] refers to an ETicket!

A type error at run time!

Madhavan Mukund Java generics and subtyping Programming Concepts using Java 2/9
Extending subtyping in contexts
If S is compatible with T, S[] is compatible with T[]
ETicket[] elecarr = new ETicket[10];
Ticket[] ticketarr = elecarr;
// OK. ETicket[] is a subtype of Ticket[]

But . . .
...
ticketarr[5] = new Ticket();
// Not OK. ticketarr[5] refers to an ETicket!

A type error at run time!


Java array typing is covariant
If S extends T then S[] extends T[]

Madhavan Mukund Java generics and subtyping Programming Concepts using Java 2/9
Generics and subtypes

Generic classes are not covariant


LinkedList<String> is not compatible with LinkedList<Object>

Madhavan Mukund Java generics and subtyping Programming Concepts using Java 3/9
Generics and subtypes

Generic classes are not covariant


LinkedList<String> is not compatible with LinkedList<Object>

The following will not work to print out an arbitrary LinkedList


public class LinkedList<T>{...}

public static void printlist(LinkedList<Object> l){


Object o;
Iterator i = l.get_iterator();
while (i.has_next()){
o = i.get_next();
[Link](o);
}

Madhavan Mukund Java generics and subtyping Programming Concepts using Java 3/9
Generics and subtypes

Generic classes are not covariant


LinkedList<String> is not compatible with LinkedList<Object>

The following will not work to print out an arbitrary LinkedList


public class LinkedList<T>{...}

public static void printlist(LinkedList<Object> l){


Object o;
Iterator i = l.get_iterator();
while (i.has_next()){
o = i.get_next();
[Link](o);
}

How can we get around this limitation?

Madhavan Mukund Java generics and subtyping Programming Concepts using Java 3/9
Generic methods

As we have seen, we can make the method generic by introducing a type variable
public class LinkedList<T>{...}

public static <T> void printlist(LinkedList<T> l){


Object o;
Iterator i = l.get_iterator();
while (i.has_next()){
o = i.get_next();
[Link](o);
}

Madhavan Mukund Java generics and subtyping Programming Concepts using Java 4/9
Generic methods

As we have seen, we can make the method generic by introducing a type variable
public class LinkedList<T>{...}

public static <T> void printlist(LinkedList<T> l){


Object o;
Iterator i = l.get_iterator();
while (i.has_next()){
o = i.get_next();
[Link](o);
}

<T> is a type quantifier: For every type T, . . .

Madhavan Mukund Java generics and subtyping Programming Concepts using Java 4/9
Generic methods

As we have seen, we can make the method generic by introducing a type variable
public class LinkedList<T>{...}

public static <T> void printlist(LinkedList<T> l){


Object o;
Iterator i = l.get_iterator();
while (i.has_next()){
o = i.get_next();
[Link](o);
}

<T> is a type quantifier: For every type T, . . .


Note that T is not actually used inside the function
We use Object o as a generic variable to cycle through the list

Madhavan Mukund Java generics and subtyping Programming Concepts using Java 4/9
Wildcards

Instead, use ? as a wildcard type variable


public class LinkedList<T>{...}

public static void printlist(LinkedList<?> l){


Object o;
Iterator i = l.get_iterator();
while (i.has_next()){
o = i.get_next();
[Link](o);
}
}

Madhavan Mukund Java generics and subtyping Programming Concepts using Java 5/9
Wildcards

Instead, use ? as a wildcard type variable


public class LinkedList<T>{...}

public static void printlist(LinkedList<?> l){


Object o;
Iterator i = l.get_iterator();
while (i.has_next()){
o = i.get_next();
[Link](o);
}
}

? stands for an arbitrary unknown type

Madhavan Mukund Java generics and subtyping Programming Concepts using Java 5/9
Wildcards

Instead, use ? as a wildcard type variable


public class LinkedList<T>{...}

public static void printlist(LinkedList<?> l){


Object o;
Iterator i = l.get_iterator();
while (i.has_next()){
o = i.get_next();
[Link](o);
}
}

? stands for an arbitrary unknown type


Avoids unnecessary type variable quantification when the type variable is not needed
elsewhere
Madhavan Mukund Java generics and subtyping Programming Concepts using Java 5/9
Wildcards

Can define variables of a wildcard type


public class LinkedList<T>{...}

LinkedList<?> l;

Madhavan Mukund Java generics and subtyping Programming Concepts using Java 6/9
Wildcards

Can define variables of a wildcard type


public class LinkedList<T>{...}

LinkedList<?> l;

But need to be careful about assigning values


public class LinkedList<T>{...}

LinkedList<?> l = new LinkedList<String>();


[Link](new Object()); // Compile time error

Madhavan Mukund Java generics and subtyping Programming Concepts using Java 6/9
Wildcards

Can define variables of a wildcard type


public class LinkedList<T>{...}

LinkedList<?> l;

But need to be careful about assigning values


public class LinkedList<T>{...}

LinkedList<?> l = new LinkedList<String>();


[Link](new Object()); // Compile time error

Compiler cannot guarantee the types match

Madhavan Mukund Java generics and subtyping Programming Concepts using Java 6/9
Bounded wildcards
Suppose Circle, Square and Rectangle all extend Shape

Madhavan Mukund Java generics and subtyping Programming Concepts using Java 7/9
Bounded wildcards
Suppose Circle, Square and Rectangle all extend Shape
Shape has a method draw()

Madhavan Mukund Java generics and subtyping Programming Concepts using Java 7/9
Bounded wildcards
Suppose Circle, Square and Rectangle all extend Shape
Shape has a method draw()
All subclasses override draw()

Madhavan Mukund Java generics and subtyping Programming Concepts using Java 7/9
Bounded wildcards
Suppose Circle, Square and Rectangle all extend Shape
Shape has a method draw()
All subclasses override draw()
Want a function to draw all elements in a list of Shape compatible objects
public static void drawAll(LinkedList<? extends Shape> l){
Object o;
Iterator i = l.get_iterator();
while (i.has_next()){
o = i.get_next();
[Link]();
}
}

Madhavan Mukund Java generics and subtyping Programming Concepts using Java 7/9
Bounded wildcards
Copying a LinkedList, using a
wildcard
public static <? extends T,T>
void listcopy (LinkedList<?> src,
LinkedList<T> tgt){
Object o;
Iterator i = srt.get_iterator();
while (i.has_next()){
o = i.get_next();
[Link](o);
}
}

Madhavan Mukund Java generics and subtyping Programming Concepts using Java 8/9
Bounded wildcards
Copying a LinkedList, using a Can reverse the constraint, using super
wildcard
public static <T,? super T>
public static <? extends T,T> void listcopy (LinkedList<T> src,
void listcopy (LinkedList<?> src, LinkedList<?> tgt){
LinkedList<T> tgt){ Object o;
Object o; Iterator i = srt.get_iterator();
Iterator i = srt.get_iterator(); while (i.has_next()){
while (i.has_next()){ o = i.get_next();
o = i.get_next(); [Link](o);
[Link](o); }
} }
}

Madhavan Mukund Java generics and subtyping Programming Concepts using Java 8/9
Summary

Java generics are not covariant, unlike arrays


Cannot substitute Object for T to get most general type
Instead, use type quantification <T> or wild card type variable ?
Wild card can be used wherever the type T is not required within the function
When T is not needed for return type, or to declare local variables

Wild cards can be bounded


LinkedList<? extends T>
LinkedList<? super T>

Madhavan Mukund Java generics and subtyping Programming Concepts using Java 9/9

You might also like