Сборщики мусора в Java

Широкий спектр приложений, от небольших апплетов на настольных компьютерах до веб-сервисов на больших серверах, использует платформу Java Standard Edition (Java SE). Для поддержки этого разнообразного развертывания виртуальная машина Java HotSpot предоставляет несколько сборщиков мусора, каждый из которых предназначен для удовлетворения различных требований. Java SE выбирает наиболее подходящий сборщик мусора в зависимости от класса компьютера, на котором запущено приложение. Однако этот выбор не может быть оптимальным для каждого приложения. Пользователям, разработчикам и администраторам со строгими целями производительности или другими требованиями может потребоваться явно выбрать сборщик мусора и настроить определенные параметры для достижения желаемого уровня производительности.

Что такое сборщик мусора?

Сборщик мусора (GC, Garbage Collector) автоматически управляет запросами приложения на динамическое выделение памяти.

Сборщик мусора выполняет автоматическое управление динамической памятью посредством следующих операций:

  • Выделяет и возвращает память операционной системе.
  • Раздает эту память приложению, когда оно его запрашивает.
  • Определяет, какие части этой памяти все еще используются приложением.
  • Восстанавливает неиспользуемую память для повторного использования приложением.

Сборщики мусора в Java HotSpot используют различные методы для повышения эффективности этих операций:

  • Использует очистку поколений вместе со старением, чтобы сосредоточить свои усилия на областях в куче (heap), которые, скорее всего, содержат много областей памяти, которые можно восстановить.
  • Использует несколько потоков для агрессивного параллельного выполнения операций или выполнения некоторых длительных операций в фоновом режиме конкурентно с приложением.
  • Пробует восстановить большую свободную непрерывную память, сжимая живые объекты.

Почему выбор сборщика мусора имеет значение?

Целью сборщика мусора является освобождение разработчика приложений от ручного управления динамической памятью. Разработчик освобождается от необходимости сопоставлять выделения с освобождениями и внимательно следить за временем жизни выделенной динамической памяти. Это полностью исключает некоторые классы ошибок, связанных с управлением памятью, за счет дополнительных накладных расходов времени выполнения. Java HotSpot VM предоставляет выбор алгоритмов сборки мусора.

Когда выбор сборщика мусора имеет значение? Для некоторых приложений ответ - никогда. То есть приложение может хорошо работать при наличии сборки мусора с паузами небольшой частоты и продолжительности. Однако это не относится к большому классу приложений, особенно с большими объемами данных (несколько гигабайт), многими потоками и высокой скоростью транзакций.

Закон Амдала (параллельное ускорение в данной проблеме ограничено последовательной частью проблемы) подразумевает, что большинство рабочих нагрузок не может быть идеально распараллелено; некоторая часть всегда последовательна и не выигрывает от параллелизма. На платформе Java в настоящее время существует четыре поддерживаемых варианта сборки мусора, и все, кроме одного, последовательного GC, распараллеливают работу для повышения производительности. Очень важно максимально снизить затраты на сборку мусора. Это можно увидеть в следующем примере.

График моделирует идеальную систему, которая отлично масштабируется, за исключением сборки мусора. Красная линия - это приложение, которое тратит только 1% времени на сборку мусора в однопроцессорной системе. Это приводит к потере пропускной способности более чем на 20% в системах с 32 процессорами. Пурпурная линия показывает, что для приложения, занимающего 10% времени при сборке мусора (не считающегося чрезмерным количеством времени при сборке мусора в однопроцессорных приложениях), более 75% пропускной способности теряется при масштабировании до 32 процессоров.

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

Последовательный коллектор (serial collector) обычно подходит для большинства небольших приложений, в частности тех, которые требуют кучи (heap) до приблизительно 100 мегабайт на современных процессорах. У других сборщиков есть дополнительные издержки или сложность, которая является ценой за специализированное поведение. Если приложению не требуется специализированное поведение альтернативного сборщика, используйте последовательный сборщик. Одной из ситуаций, когда последовательный сборщик не должен быть лучшим выбором, является большое, многопоточное приложение, которое работает на машине с большим объемом памяти и двумя или более процессорами. Когда приложения запускаются на таких машинах серверного класса, сборщик Garbage-First (G1) выбирается по умолчанию.

Комментарии

Популярные сообщения из этого блога

Методы класса Object в Java

Как получить текущий timestamp в Java

Основные опции JVM для повышения производительности и отладки