Подтвердить что ты не робот

Что означает список <?> В java generics?

Что означает List<?>, означает ли это просто список объектов неопределенного типа?

Googling для строки <?> не возвращает ничего полезного (:

4b9b3361

Ответ 1

Ключевое слово, необходимое для получения дополнительной информации, Wildcards

Ответ 2

Как сказал Том, ? или неограниченный подстановочный знак означает, что тип объекта не указан. Это может быть неизвестно, может быть рассчитано на несколько возможных значений или может быть просто неуместным. Ваш пример, List<?>, произносится как "Список неизвестных". Это удобно, потому что оно гибкое, но есть и некоторые подводные камни, потому что вы не можете засунуть случайные объекты и вытащить их из групп неизвестных с полной безнаказанностью.

Ресурсы

  • Подстановочные знаки обсуждаются здесь в учебнике по Java.
  • Там хорошо - если многословный - учебник по дженерикам вообще Анжелики Лангер доступен здесь.
  • И еще один хороший обзор здесь (PDF) Гилада Брача; просмотрите страницы 5-7.
  • Наконец, если вы можете получить эффективную Java от Джоша Блоха, он получил отличный раздел о дженериках, а случаи, в которых вы можете, не можете, должны и не должны использовать подстановочные знаки (глава 5, стр. 109 -146 во втором издании).

Кстати, ваш поиск Google не удался, потому что Google не вывоз со специальными символами:

За некоторыми исключениями пунктуация игнорируется (т.е. вы не можете искать @# $% ^ & *() = + []\и другие специальные символы).

- Страница справки Google

(EDIT: Я, должно быть, очень устал, когда писал это вчера вечером. Убрал форматирование/добавил немного информации.)

Ответ 3

Чтобы ответить на этот вопрос, мне нужно объяснить неограниченные символы и ограниченные символы.
Содержание этого поста было собрано из документации Java.

1. Неограниченные символы

Неограниченный подстановочный тип указывается с использованием подстановочного знака (?), например, List<?>. Это называется списком неизвестного типа. Существует два сценария, в которых неограниченный подстановочный знак является полезным подходом:

  • Если вы пишете метод, который может быть реализован с использованием функций, предоставляемых в классе Object.

  • Когда код использует методы в общем классе, которые не зависят от параметра типа. Например, List.size или List.clear. На самом деле, Class<?> так часто используется, потому что большинство методов в Class<T> не зависят от T.

2. Ограниченные шаблоны

Рассмотрим простое приложение для рисования, которое может рисовать фигуры, такие как прямоangularьники и круги. Чтобы представить эти фигуры в программе, вы можете определить иерархию классов, например:

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) {
        ...
    }
}

Эти классы могут быть нарисованы на холсте:

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

Любой рисунок обычно содержит несколько фигур. Предполагая, что они представлены в виде списка, было бы удобно иметь метод в Canvas, который их всех рисует:

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

Теперь правила типа говорят, что drawAll() можно вызывать только в списках точно Shape: его нельзя, например, вызывать в List<Circle>. Это прискорбно, так как все, что делает метод - это считывает фигуры из списка, поэтому его можно также вызывать для List<Circle>. Что нам действительно нужно, так это чтобы метод принимал список любой формы:     public void drawAll (Список фигур) {         ...     } Здесь есть небольшое, но очень важное отличие: мы заменили тип List<Shape> на List<? extends Shape>. Теперь drawAll() будет принимать списки любого подкласса Shape, поэтому теперь мы можем вызвать его на List<Circle>, если захотим.

List<? extends Shape> является примером ограниченного символа подстановки. ? обозначает неизвестный тип, однако в этом случае мы знаем, что этот неизвестный тип фактически является подтипом Shape. (Примечание. Это может быть сам Shape или некоторый подкласс; ему не нужно буквально расширять Shape.) Мы говорим, что Shape является верхней границей подстановочного знака.

Точно так же синтаксис ? super T, который является ограниченным подстановочным знаком, обозначает неизвестный тип, который является супертипом T. ArrayedHeap280<? super Integer>, например, включает в себя ArrayedHeap280<Integer>, ArrayedHeap280<Number> и ArrayedHeap280<Object>. Как вы можете видеть в документации Java для класса Integer, Integer является подклассом Number, который, в свою очередь, является подклассом Object.

Ответ 4

Похоже, вы должны искать документацию по генеалогическим файлам Java.

List<?> означает, что это объект, основанный на текущем неуказанном типе. Эта спецификация создается при создании экземпляра класса.

Например:

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

- список объектов String.

Ответ 5

List - это интерфейс, который вы можете реализовать самостоятельно, а также реализован некоторыми наборами Java, например Vector.

Вы можете предоставить информацию о времени компиляции, используя угловые скобки. Наиболее общим типом будет Object, который будет List<Object>. <?>, который вы видите, указывает список некоторых подклассов Object или Object. Это как сказать List<? extends Object> или List<? extends Foo>, где List содержит объекты некоторого подкласса Foo или объекты самого Foo.

Вы не можете создать экземпляр List; это интерфейс, а не реализация.

Ответ 6

List<?> означает List<? extends Object>, поэтому в Collection<E> вы найдете containsAll(Collection<?> c), который позволяет вам писать

List<Object> objs = Arrays.<Object>asList("one",2,3.14,4);
List<Integer> ints = Arrays.asList(2,4);
assert objs.containsAll(ints);//true

Ответ 7

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

Generics предоставляет вам способ передать тип коллекции компилятору, чтобы его можно было проверить. После того, как компилятор знает тип элемента коллекции, компилятор может проверить, что вы использовали коллекцию последовательно и можете вставить правильные отбрасывания на значения, извлекаемые из коллекции.

chk dis pdf

Ответ 8

? не что иное, как Wildcard в Generics

В Generics есть 3 разных вида символов подстановки

1) Подстановочные знаки с верхним ограничением: используется расширяет ключевое слово

eg: List<? extends SuperClass>

2) Подстановочные знаки с нижним ограничением

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

3) Неограниченный шаблон

List<?> list

Ответ 9

Вероятно, вы ищете шаблон на основе List. Вы можете создать список строк List<String> myList = new MyList<String>(); в качестве примера. Проверьте документацию на все типы, которые она поддерживает. Он должен поддерживать любой тип объекта, но если есть функция сортировки, вы должны предоставить некоторые функции сравнения.

Обратите внимание, что в приведенном выше примере MyList - это конкретный класс, реализующий интерфейс List в Java. Это может быть ArrayList.

EDIT: Я предположил List как конкретный класс по ошибке. Исправлена ​​ошибка выше. Спасибо, Джон.