What does List<?> mean in java generics?
Asked Answered
A

11

63

What does List<?> mean, does it mean simply a list of objects of unspecified type?

Googling for the string <?> returns nothing useful (:

Allistir answered 4/12, 2009 at 4:2 Comment(0)
S
37

The keyword you need to get more information is Wildcards

Scaffolding answered 4/12, 2009 at 4:5 Comment(0)
S
60

As Tom said, the ?, or unbounded wildcard, means that the type of the object is not specified. It could be unknown, could be meant for multiple possible values or might be just plain irrelevant. Your example, List<?>, is pronounced "List of unknown." It's convenient because it's flexible, but there are also some pitfalls because you can't shove random objects in and pull them out of groups of unknown with total impunity.

Resources:

  • Wildcards are discussed here in the Java tutorial.
  • There's a good -- if verbose -- tutorial on generics in general by Angelika Langer available here.
  • And there's another good overview here (PDF) by Gilad Bracha; check out pages 5-7.
  • Finally, if you can get your hands on Effective Java by Josh Bloch, it's got a great section on generics and the cases in which you can, can't, should and shouldn't use wildcards (chapter 5, pages 109-146 in the second edition).

Incidentally, your Google search failed because Google doesn't truck with special characters:

With some exceptions, punctuation is ignored (that is, you can't search for @#$%^&*()=+[]\ and other special characters).

-Google help page

(EDIT: I must have been really tired when I wrote this last night. Cleaned up formatting/added a little info.)

Stramonium answered 4/12, 2009 at 4:20 Comment(0)
S
37

The keyword you need to get more information is Wildcards

Scaffolding answered 4/12, 2009 at 4:5 Comment(0)
F
19

To answer this question I need to explain Unbounded Wildcards and Bounded Wildcards.
The content of this post has been assembled from java documentation.

1. Unbounded Wildcards

The unbounded wildcard type is specified using the wildcard character (?), for example, List<?>. This is called a list of unknown type. There are two scenarios where an unbounded wildcard is a useful approach:

  • If you are writing a method that can be implemented using functionality provided in the Object class.

  • When the code is using methods in the generic class that don't depend on the type parameter. For example, List.size or List.clear. In fact, Class<?> is so often used because most of the methods in Class<T> do not depend on T.

2. Bounded Wildcards

Consider a simple drawing application that can draw shapes such as rectangles and circles. To represent these shapes within the program, you could define a class hierarchy such as this:

public abstract class Shape {
    public abstract void draw(Canvas c);
}

public class Circle extends Shape {
    private int x, y, radius;
    public void draw(Canvas c) {
        ...
    }
}

public class Rectangle extends Shape {
    private int x, y, width, height;
    public void draw(Canvas c) {
        ...
    }
}

These classes can be drawn on a canvas:

public class Canvas {
    public void draw(Shape s) {
        s.draw(this);
   }
}

Any drawing will typically contain a number of shapes. Assuming that they are represented as a list, it would be convenient to have a method in Canvas that draws them all:

public void drawAll(List<Shape> shapes) {
    for (Shape s: shapes) {
        s.draw(this);
   }
}

Now, the type rules say that drawAll() can only be called on lists of exactly Shape: it cannot, for instance, be called on a List<Circle>. That is unfortunate, since all the method does is read shapes from the list, so it could just as well be called on a List<Circle>. What we really want is for the method to accept a list of any kind of shape: public void drawAll(List shapes) { ... } There is a small but very important difference here: we have replaced the type List<Shape> with List<? extends Shape>. Now drawAll() will accept lists of any subclass of Shape, so we can now call it on a List<Circle> if we want.

List<? extends Shape> is an example of a bounded wildcard. The ? stands for an unknown type, however, in this case, we know that this unknown type is in fact a subtype of Shape. (Note: It could be Shape itself, or some subclass; it need not literally extend Shape.) We say that Shape is the upper bound of the wildcard.

Similarly, the syntax ? super T, which is a bounded wildcard, denotes an unknown type that is a supertype of T. A ArrayedHeap280<? super Integer>, for example, includes ArrayedHeap280<Integer>, ArrayedHeap280<Number>, and ArrayedHeap280<Object>. As you can see in the java documentation for Integer class, Integer is a subclass of Number that in turn is a subclass of Object.

Frig answered 30/1, 2017 at 3:54 Comment(0)
S
4
  • List: There is no type restriction and assignment restriction at all.
  • List<Object>: It seems to be used the same as List, but a compilation error will occur when accepting other generic assignments.
  • List<?>: It is a generic type. Before assignment, it means that it can accept any type of set assignment, but after assignment, you can't add elements to it, but you can remove and clear, not an immutable set. List<?> is generally used as a parameter to receive an external collection, or return a collection of specific element types, also known as a wildcard collection.

The test code and result as followed:

        List a1 = new ArrayList();
        a1.add(new Object());
        a1.add(new Integer(10));
        a1.add(new String("string"));

        System.out.println("List is : " + a1);

        List<?> a4 = a1;
        a4.remove(0);
        System.out.println("List is : " + a4);

        System.out.println("List is : " + a4.get(0));
        
        a4.clear();
        System.out.println("List is : " + a4);

The result is :

List is : [java.lang.Object@2a139a55, 10, string]
List is : [10, string]
List is : 10
List is : []
Selby answered 19/7, 2020 at 13:26 Comment(0)
R
3

Sounds like you should look for some documentation on Java generics.

The List<?> means that it is an object based on a currently unspecified type. That specification is made when the class is instantiated.

For example:

List<String> listOfStrings = new ArrayList<String>();

is a list of String objects.

Riddell answered 4/12, 2009 at 4:8 Comment(1)
I don't see the connection btw List<String> listOfStrings = new ArrayList<String>(); and List<?>Ermina
H
3

List is an interface you can implement yourself and also implemented by some of the Java collections, like Vector.

You can provide compile-time typing information using the angled brackets. The most generic type would be Object, which would be List<Object>. The <?> you see is indicating a List of some subclass of Object or an Object. This is like saying List<? extends Object>, or List<? extends Foo>, where the List contains objects of some subclass of Foo or objects of Foo itself.

You can't instantiate a List; it's an interface, not an implementation.

Hertzog answered 4/12, 2009 at 4:13 Comment(0)
E
3

List<?> stands for List<? extends Object> so in Collection<E> you will find containsAll(Collection<?> c) which allows you to write

List<Object> objs = Arrays.<Object>asList("one",2,3.14,4);
List<Integer> ints = Arrays.asList(2,4);
assert objs.containsAll(ints);//true
Ermina answered 4/12, 2009 at 4:26 Comment(0)
O
0

When you take an element out of a Collection, you must cast it to the type of element that is stored in the collection. Besides being inconvenient, this is unsafe. The compiler does not check that your cast is the same as the collection's type, so the cast can fail at run time.

Generics provides a way for you to communicate the type of a collection to the compiler, so that it can be checked. Once the compiler knows the element type of the collection, the compiler can check that you have used the collection consistently and can insert the correct casts on values being taken out of the collection.

chk dis pdf

Outsider answered 4/12, 2009 at 5:16 Comment(0)
S
0

? is nothing but Wildcard in Generics

There are 3 different kind of Wildcards in Generics

1) Upper Bounded Wildcards: Uses extends key word

eg: List<? extends SuperClass>

2) Lower Bounded Wildcards

eg:Uses Super key word List<? super SubClass>

3) Unbounded Wildcard

List<?> list
Spanos answered 26/7, 2019 at 13:36 Comment(0)
J
0

List<?> is equivalent to List<? extends Object>

The wildcard ? extends Object is equivalent to the unbounded wildcard ?

<?> in java specification

Generics in java specification

Jitter answered 4/4, 2021 at 18:49 Comment(0)
N
-1

You are probably looking at the template based List class. You can create a list of strings by List<String> myList = new MyList<String>(); as an example. Check the documentation for all the types it supports. It should support any object type, but if there is a sort functionality you have to supply some compare functions.

Note that in the example above MyList is a concrete class that implements the List interface in Java. It can be ArrayList.

EDIT: I assumed List as a concrete class by mistake. Fixed the error above. Thanks Jon.

Nottingham answered 4/12, 2009 at 4:10 Comment(2)
You have to instantiate something that implements List, like ArrayList or Vector.Tacita
Just to clarify, Java uses generics, not templates.Epicardium

© 2022 - 2024 — McMap. All rights reserved.