Сборка мусора (Garbage Collection, GC) — это автоматическое управление памятью, которое ищет и освобождает память, занятую объектами, которые больше не используются программой.
Основные принципы работы GC:
-
Определение достижимости объектов: GC определяет, к каким объектам программа может получить доступ из "корней сборки мусора" (например, глобальные переменные, локальные переменные текущих потоков). Объекты, достижимые из этих корней через цепочки ссылок, считаются "живыми".
-
Сбор неиспользуемых объектов: Объекты, которые не являются "живыми" (то есть, на них нет ссылок от "корней" или других "живых" объектов), считаются "мусором" и подлежат освобождению.
-
Освобождение памяти: GC освобождает память, занятую "мусором", делая ее доступной для создания новых объектов.
Типы алгоритмов GC:
- Reference Counting (Подсчет ссылок): Каждый объект имеет счетчик ссылок на него. Когда счетчик достигает нуля, объект считается "мусором". Прост в реализации, но не справляется с циклическими ссылками.
- Mark and Sweep (Пометка и удаление):
- Marking (Пометка): Начиная от "корней", GC обходит граф объектов и помечает все "живые" объекты.
- Sweeping (Удаление): GC проходит по всей куче памяти и освобождает место, занятое непомеченными объектами. Может приводить к фрагментации памяти.
- Mark and Compact (Пометка и сжатие): После пометки "живых" объектов, GC перемещает их в начало кучи, освобождая непрерывный блок памяти. Снижает фрагментацию.
- Copying (Копирование): Делит кучу на два пространства. Во время сборки мусора "живые" объекты копируются из одного пространства в другое. Быстрый для короткоживущих объектов, но требует вдвое больше памяти.
- Generational GC (Поколенческая GC): Делит кучу на несколько "поколений". Основан на предположении, что большинство объектов короткоживущие. Сборка мусора чаще производится в "младших" поколениях (где создаются новые объекты).
В Android (JVM/ART) чаще всего используется generational GC с различными оптимизациями (например, concurrent collectors, которые работают параллельно с основным потоком приложения).
Особенности JVM/ART GC:
- Работает на отдельном потоке или параллельно с приложением.
- Может вызывать "паузы" в работе приложения во время сборки мусора (хотя современные алгоритмы минимизируют их).
- Не гарантирует моментального освобождения памяти после того, как объект станет недостижимым.
Пример недостижимого объекта:
java