Почему разные коллекции Java имеют различную емкость по умолчанию?


11

Глядя на разных конструкторов коллекций, возникает вопрос. Почему ArrayList () создает пустой список с начальной емкостью десять, а ArrayDeque () создает пустой массив массивов с начальной емкостью, достаточной для хранения 16 элементов.


У меня не было нового, у которого был предел мощности. Я просто добавляю новые элементы с помощью add (). Это всегда работает.
Тулин Кордова

1
Я думаю, что он говорит о начальном размере массива в реализации ArrayList. Как следует из его названия, ArrayList - это просто старый массив под обложками, и он автоматически создает большие массивы, когда вы пытаетесь добавить больше элементов, чем содержит его текущий размер массива.
dsw88

1
Я думаю, что StringBuilder - еще один, у которого есть емкость по умолчанию, это было 10 или 16?
Инго

@ Инго Интересно. Я даже не знал о вещах вне коллекций, перепутанных с емкостью, но я полагаю, что это имеет смысл. В то время не было метки для емкости, поэтому я не особо интересовался другими видами использования.
Старый Бадман Грей

Ответы:


17

Краткий ответ

Поскольку емкость ArrayDeque должна быть степенью двойки, а 16 - это наименьшая степень двойки, равная по меньшей мере 10.


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

a % bможет быть выражено, как a & (b - 1) будто b это степень двух. Побитовое И значительно быстрее, поэтому емкость ArrayDeque ограничена степенью двойки. Все операции% выполняются с битовой маскировкой вместо фактического% в реализации.

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

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


3

Не исключайте возможности того, что нет конкретной причины.

Возможно, эти две коллекции были написаны разными командами. Оба выбрали небольшое число в качестве емкости по умолчанию, но первая команда думала десятично и выбирала 10, а вторая команда думала двоично и выбирала 16.


1

Ответ @ Esailija хорош для этого конкретного случая.

В более общем смысле, это компромисс, который зависит от многих факторов. Я приведу несколько примеров:

  • Как обычно используется структура данных ? Структуры данных, которые используются в качестве буферов данных, обычно предпочитают гораздо более высокую емкость, чем структуры данных, используемые, например, для небольших кортежей.
  • Какой размер данных по умолчанию помещается в строку кэша на целевой платформе ЦП? Это может иметь большое значение для производительности, если значение по умолчанию помещается в строку кэша. Выбор 10 по умолчанию в Java вполне может быть обусловлен тем, что массив из 10 32-битных слов плюс издержки массива / объекта помещаются в 64-байтовую строку кэша.
  • Сколько вы цените пространство против эффективности времени выполнения ? Если вам нужна лучшая производительность во время выполнения, обычно лучше заранее выделить больше места, чтобы впоследствии избежать дополнительных перераспределений.

В результате этих компромиссов вполне понятно, что разные реализации коллекций могут иметь различную оптимальную емкость по умолчанию.

Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.