Сборщики мусора HotSpot

Сборщик выбирают под цель: throughput, короткие паузы, размер heap и доступный CPU. Набор и поведение зависят от версии и сборки JVM.

CollectorОсновная цельХарактер
Serialпростота, маленький heapодин GC-поток, STW
Parallelthroughputпараллельные STW-сборки
G1баланс latency/throughputregion-based, часть работы concurrent
ZGCочень короткие паузыбольшая часть работы concurrent
Shenandoahкороткие паузыconcurrent evacuation, не во всех дистрибутивах
Epsilonне освобождает памятьтесты, измерения, короткие процессы

G1 — типичный default в современных server-конфигурациях HotSpot, но полагаться на предположение нельзя: проверяю фактические JVM flags и logs.

CMS — legacy-сборщик: он был deprecated, затем удалён из JDK. В старых конспектах и системах его всё ещё можно встретить, но для нового развёртывания он не вариант.

Выбор по данным

1. Зафиксировать SLO по latency и throughput.
2. Включить и сохранить GC logs.
3. Измерить allocation rate, live set, паузы, CPU.
4. Сначала убрать удержание/лишние аллокации.
5. Менять collector или heap одним контролируемым экспериментом.

Примеры запуска:

java -XX:+UseG1GC -Xlog:gc*:file=gc.log:time,level,tags App
java -XX:+UseZGC -Xlog:gc App

Флаг из другой версии JVM может отсутствовать или менять смысл. Проверять нужно на той же JVM, что работает в production.

Ошибки

  • выбирать collector только по среднему времени паузы;
  • ставить огромный heap без оценки live set и времени восстановления;
  • считать высокую частоту young GC проблемой сама по себе;
  • лечить утечку увеличением -Xmx;
  • сравнивать результаты без одинаковой нагрузки и прогрева.

На собеседовании

Чем Parallel отличается от low-latency collectors? Он оптимизирует общую производительность ценой STW-пауз.

Есть ли полностью pauseless GC? Нет, остаются хотя бы короткие точки синхронизации.

Что делает Epsilon? Выделяет память и не собирает мусор до исчерпания heap.

Как выбрать GC? По SLO и измерениям на репрезентативной нагрузке.

Связано: Процесс сборки мусора, Garbage collector.