2010-12-06 4 views
5

Я знаю, что для того, чтобы создать объект ArrayList типа мне нужно:ArrayList (Collection <? extends E> с)

ArrayList<MyType> l = new ArrayList<MyType>(); 

Я это знаю, потому что я видел это в книгах.

Но, глядя на Java SE API для конструктора ArrayList я вижу: ArrayList(Collection<? extends E> c)

Я не понимаю, как бы я когда-либо получить представление о том, чтобы указать тип объектов, мой новый объект ArrayList будет держать? Как мне узнать из этого определения, что я должен указать <MyType> во время создания экземпляра и объявления переменной?

+1

Где вы ищете, потому что я вижу: «общественное ArrayList (Collection с)» – jzd 2010-12-06 19:23:27

+0

@jzd, это то, что ОП ставить уже на этот вопрос .... – 2010-12-06 19:25:38

ответ

3

Чтобы узнать, нужны ли параметры типа в декларации, вы не смотрите на конструктор, вы смотрите на class definition itself. Аргументы конструкторов не имеют никакого отношения к типу самого объекта - конструктор может принимать любые аргументы, как и любой другой метод. Вот определение класса:

public class ArrayList<E> 
extends AbstractList<E> 
implements List<E>, RandomAccess, Cloneable, Serializable 

class ArrayList<E> часть говорит, что есть класс, называемый ArrayList и требует один параметр типа (который называется Е здесь).

4

Этот метод предназначен для копирования существующего экземпляра коллекции в новый ArrayList, который нельзя создавать с нуля. Элементы коллекции, которые он примет, имеют верхнюю границу типа E, которая тогда будет типом вашего нового ArrayList.

1

Это всегда так, когда вы строите объект для класса, который принимает общий тип. Если вы прокрутите вверх до вершины, вы увидите Class ArrayList < E>. Это намек.

2

Предположим, у вас есть набор классов формы. Базовый класс - Shape, а две реализации: Square и Circle. Теперь, после того, как вы сделали определенную настройку для списка объектов, которые вы хотели, вам нужно добавить все это вместе, чтобы отправить его в функцию рендеринга. Приведенный ниже код должен делать то, что я описываю немного более ясно:

ArrayList<Square> squares = readSquares(); 
ArrayList<Circle> circles = readCircles(); 

ArrayList<Shape> queue= new ArrayList<Shape>(squares); 
queue.addAll(circles); 

renderShapes(queue); 

ArrayList(Collection<? extends E> c) конструктор делает линию пяти возможных. В случае дженериков процессор недостаточно умен, чтобы автоматически определять, что Square расширяет форму по умолчанию. Вы должны сказать компилятору, что вы намеревались. Как вы это делаете, с подстановочным знаком <? extends E>. Теперь компилятор будет следить за тем, чтобы каждый добавленный объект был по крайней мере Shape.