1. Введение
Всякий раз, когда мы объявляем переменную или создаем объект, он сохраняется в памяти. На высоком уровне Java делит память на два блока: стек и кучу . Обе памяти хранят определенные типы данных и имеют разные схемы их хранения и доступа.
В этом руководстве мы рассмотрим различные параметры и узнаем, какая область является наиболее подходящей для хранения пула констант String .
2. Пул строковых констант
Пул констант String
— это специальная область памяти. Когда мы объявляем строковый
литерал, JVM создает объект в пуле и сохраняет его ссылку в стеке. Перед созданием каждого объекта String
в памяти JVM выполняет несколько шагов, чтобы уменьшить нагрузку на память. `` ``
Пул констант String использует в своей реализации Hashmap .
Каждое ведро Hashmap
содержит список String
с одинаковым хеш-кодом. В более ранних версиях Java область хранения для пула имела фиксированный размер и часто могла приводить к ошибке « Не удалось зарезервировать достаточно места для кучи объектов » .
Когда система загружает классы, строковые
литералы всех классов переходят в пул уровня приложения. Это связано с тем, что одинаковые строковые
литералы разных классов должны быть одним и тем же Object
. В этих ситуациях данные в пуле должны быть доступны каждому классу без какой-либо зависимости.
Обычно в стеке хранятся недолговечные данные. Он включает в себя локальные примитивные переменные, ссылки на объекты кучи и выполняемые методы. Куча обеспечивает динамическое выделение памяти, сохраняет объекты Java и классы JRE во время выполнения.
Куча обеспечивает глобальный доступ, и хранилища данных в куче доступны для всех потоков в течение всего времени существования приложения, тогда как хранилища данных в стеке имеют частную область действия, и только поток-владелец может получить к ним доступ.
Стек хранит данные в смежных блоках памяти и допускает произвольный доступ. Если классу требуется случайная строка
из пула, она может быть недоступна из-за правила стека LIFO (последним пришел — первым ушел). Напротив, куча динамически выделяет память и позволяет нам получать доступ к данным любым способом.
Предположим, у нас есть фрагмент кода, состоящий из разных типов переменных. В стеке будет храниться значение литерала int
и ссылки на объекты String
и Demo .
Значение любого объекта будет храниться в куче, а все строковые
литералы помещаются в пул внутри кучи:
Переменные, созданные в стеке, освобождаются, как только поток завершает выполнение. Напротив, сборщик мусора восстанавливает ресурсы в куче. Точно так же сборщик мусора собирает элементы, на которые нет ссылок, из пула.
Размер пула по умолчанию может отличаться на разных платформах. В любом случае, он все равно намного больше доступного размера стека. До JDK 7 пул был частью пространства permgen, а начиная с JDK 7 и до сих пор он является частью основной памяти кучи.
3. Заключение
В этой короткой статье мы узнали об области хранения для пула констант String .
Стек и куча имеют разные характеристики для хранения данных и доступа к ним. От выделения памяти до ее доступа и доступности куча является наиболее подходящей областью для хранения пула констант String.
На самом деле пул никогда не был частью стековой памяти.