Ответ
Garbage Collector (GC) в Java освобождает память, когда объект становится недостижимым (нет активных ссылок). Основные сценарии:
- Локальные переменные – после выхода из метода.
- Null-ссылки – присвоение
nullделает объект кандидатом на сборку. - Переприсвоение ссылки – старая ссылка теряется.
- Изолированные объекты – циклические ссылки без внешних связей.
Пример:
void example() {
Object obj1 = new Object(); // 1. Создаем объект
Object obj2 = new Object(); // 2. Еще один объект
obj1 = obj2; // 3. obj1 теперь ссылается на obj2, старый объект доступен для GC
obj2 = null; // 4. obj2 = null, но obj1 еще держит ссылку
} // 5. После выхода из метода все локальные ссылки теряются – GC может собрать объекты
Важно: GC работает не мгновенно, а по мере необходимости или при нехватке памяти.
Ответ 18+ 🔞
Давай разберёмся с этим вашим сборщиком мусора, а то народ пугается, как будто это какой-то демон из ада. Вообще, штука полезная, но работает она по своим, иногда загадочным, правилам.
Представь, что твоя оперативка — это комната в общаге. Ты там живёшь, тусуешься, создаёшь объекты — new Object(). Это как притащить в комнату новый стул, гитару или бутылку пива. Пока ты на эту вещь смотришь (то есть есть на неё ссылка), она твоя. Стоит и стоит.
А теперь сценарии, когда эта хрень становится мусором и её можно выкинуть (собрать GC):
-
Локальные переменные. Ты в методе
void getDrunk()создал локальную переменнуюBeer b = new Beer("Baltica"). Выпил, вышел из метода — и всё, про эту бутылку ты забыл. Сборщик мусора, видя, что на неё никто не ссылается, её благополучно выносит на помойку. Ёпта, логично же. -
Null-ссылки. Была у тебя крутая ссылка на объект
Girlfriend gf = new Girlfriend("Наташа"). Потом ты ей позвонил, она сказала "у нас нет будущего". Ты пишешь в кодеgf = null;. Всё, Наташа официально стала кандидатом на удаление из памяти. Жестоко, но справедливо. -
Переприсвоение. Была у тебя ссылка
carна старенькую "девятку". Потом ты разбогател и написалcar = new Porsche();. На "девятку" больше нет ссылки. Она теперь не твоя, и её можно утилизировать. Старое железо — на свалку истории. -
Изолированные объекты (циклические ссылки). Вот это многих вводит в ступор. Смотри: есть два друга-алкаша, Вася и Петя. У Васи есть ссылка на Петю (
vasya.friend = petya), а у Пети — на Васю (petya.friend = vasya). Они вдвоём в замкнутом цикле, но больше НИКТО в программе о них не знает. Они сидят в углу комнаты и бухают, но для внешнего мира их как бы нет. Ни хуя себе, да? Так вот, GC — он умный, он это видит. Поскольку на эту парочку нет ссылок извне, он их спокойно собирает обоих, несмотря на то, что они ссылаются друг на друга. Главное — отрезать от "корней" программы.
Смотри на этот пример, тут всё наглядно:
void example() {
Object obj1 = new Object(); // 1. Создали первый стул в комнате
Object obj2 = new Object(); // 2. Создали второй стул
obj1 = obj2; // 3. Внимание! Теперь obj1 смотрит на второй стул. А на первый стул ссылок ВООБЩЕ НЕТ. Он уже мусор!
obj2 = null; // 4. Обнулили ссылку на второй стул, но ведь obj1 всё ещё на него смотрит! Так что он пока жив.
} // 5. Выходим из метода. Все локальные переменные (obj1, obj2) уничтожаются. Теперь НИКТО не ссылается ни на первый стул (он уже давно мусор), ни на второй. Всё, оба можно выкидывать.
И главное, что нужно понять — терпения ноль ебать! GC не работает по щелчку пальцев. Он ленивая жопа. Он собирает мусор тогда, когда захочет: обычно когда память на исходе и нужно место для новых объектов. Ты можешь предложить ему поработать (System.gc()), но это всего лишь намёк, а не приказ. Он тебе в ответ: "Да похуй, соберу когда созрею".
Так что живи спокойно, создавай объекты, но просто знай — за тобой приберут. Не сразу, но приберут.