Ответ
Retain Cycle (Цикл сильных ссылок) — это частный случай утечки памяти, когда два или более объекта удерживают друг друга через strong ссылки, создавая изолированный граф. ARC не может освободить такие объекты, так как счетчики ссылок никогда не достигают нуля.
Memory Leak (Утечка памяти) — более общее понятие, обозначающее любую ситуацию, когда выделенная память не освобождается, хотя больше не нужна программе. Retain cycle — одна из самых распространенных причин утечек в Swift.
Пример retain cycle
class Person {
var apartment: Apartment?
// ...
}
class Apartment {
var tenant: Person? // СИЛЬНАЯ ссылка -> Потенциальный цикл!
// ...
}
var john: Person? = Person()
var unit4A: Apartment? = Apartment()
john!.apartment = unit4A // Person strong -> Apartment
unit4A!.tenant = john // Apartment strong -> Person
// ЦИКЛ СОЗДАН!
john = nil
unit4A = nil
// Оба объекта НЕ освобождены! Утечка памяти.
Решение: weak и unowned ссылки
Используйте weak или unowned, чтобы разорвать цикл сильных ссылок.
weak: Используется, когда ссылка может статьnilв будущем (опциональная ссылка).class Apartment { weak var tenant: Person? // Теперь weak ссылка } // Когда `john = nil`, ARC освобождает Person. // Свойство `tenant` в unit4A автоматически становится nil.unowned: Используется, когда ссылка никогда не станетnilв течение времени жизни объекта. Небезопасно, если объект уже освобожден.class Customer { var card: CreditCard? } class CreditCard { unowned let customer: Customer // Карта не может существовать без Клиента init(customer: Customer) { self.customer = customer } }
Другие причины memory leak
- Незарегистрированные observers (
NotificationCenter, KVO). - Сильные ссылки на
selfвнутри замыканий (closure), захваченных объектом. Решение: использовать capture lists[weak self]или[unowned self]. - Утечки в C-библиотеках или низкоуровневом коде.