Java HashMap.clear (), и удалите () эффективную память?

Рассмотрите follwing HashMap.clear() код:

 /**
 * Removes all of the mappings from this map.
 * The map will be empty after this call returns.
 */
public void clear() {
    modCount++;
    Entry[] tab = table;
    for (int i = 0; i < tab.length; i++)
        tab[i] = null;
    size = 0;
}

Это кажется, что внутренний массив (table) из Entry объекты никогда не shrinked. Так, когда я добавляю 10 000 элементов к карте, и после того вызова map.clear(), это сохранит 10000, аннулирует в, он - внутренний массив. Так, мой вопрос, как JVM обрабатывает этот массив ничего, и таким образом, HashMap эффективная память?

42
задан Joe Doyle 30 April 2012 в 23:33
поделиться

4 ответа

Идея в том, что clear() вызывается только тогда, когда вы хотите повторно использовать HashMap. Повторное использование объекта должно происходить только по той же причине, по которой он использовался ранее, поэтому есть шанс, что у вас будет примерно одинаковое количество записей. Чтобы избежать бесполезного сжатия и изменения размеров Map, при вызове clear() емкость остается неизменной.

Если все, что вы хотите сделать, это выбросить данные в Map, то вам не нужно (и фактически не следует) вызывать clear() для нее, а просто очистить все ссылки на саму Map, в этом случае она будет собрана в мусор.

62
ответ дан 26 November 2019 в 23:42
поделиться

Вы правы, но, учитывая, что увеличение массива - гораздо более дорогостоящая операция, HashMap вполне может подумать, что «когда пользователь увеличил array, скорее всего, ему снова понадобится массив этого размера позже », и он просто оставит массив вместо того, чтобы уменьшать его и рисковать, что позже придется снова дорого расширить его. Думаю, это эвристика - вы могли бы посоветовать и наоборот.

4
ответ дан 26 November 2019 в 23:42
поделиться

Еще нужно учитывать, что каждый элемент в table - это просто ссылка. Установка этих записей в null удалит ссылки из элементов вашей Map, которые затем будут освобождены для сборки мусора. Таким образом, вы не освобождаете память вообще.

Однако, если вам нужно освободить даже память, используемую самой Map, то вы должны освободить ее в соответствии с предложением Йоахима Зауэра.

4
ответ дан 26 November 2019 в 23:42
поделиться

Глядя на исходный код, кажется, что HashMap никогда не уменьшается. Метод resize вызывается для удвоения размера, когда это необходимо, но не имеет ничего общего с ArrayList.trimToSize().

Если вы используете HashMap таким образом, что он часто увеличивается и уменьшается, вы можете захотеть просто создать новый HashMap вместо вызова clear().

10
ответ дан 26 November 2019 в 23:42
поделиться
Другие вопросы по тегам:

Похожие вопросы: