Producer Extends, Consumer Super (PECS)

I always remember-and-forget about this Java Generics concept. So I will put it here as easy reference lookup for me.

public static <T> T max(Collection<? extends T> coll, Comparator<? super T> comp)

question : why is it Comparator<? super T> instead of Comparator<? extends T> ?

answer:

Josh Bloch's mnemonic PECS is useful here. It stands for:

Producer extends, Consumer super

This means that when a parameterized type being passed to a method will produce instances of T (they will be retrieved from it in some way), ? extends T should be used, since any instance of a subclass of T is also a T.

When a parameterized type being passed to a method will consume instances of T (they will be passed to it to do something), ? super T should be used because an instance of T can legally be passed to any method that accepts some supertype of T. A Comparator<Number> could be used on a Collection<Integer>, for example. ? extends T would not work, because a Comparator<Integer> could not operate on a Collection<Number>.

Edit: To clarify a little more on get/put (produce/consume):
public T something();
The above is a method that produces T.

public void something(T t);
The above is a method that consumes T.

"Producer extends, Consumer super" applies to how the method a parameterized object is being passed to is going to be using that object. In the case of Collections.max(), items will be retrieved from the Collection, so it is a producer. Those items will be passed as arguments to the method on Comparator, so it is a consumer.

reference : http://stackoverflow.com/questions/2248390/java-generics-collections-max-signature-and-comparator/2248503#2248503

0 comments:

Post a Comment