Ответ
Retain cycle возникает, когда два или более объекта удерживают друг друга через strong-ссылки, предотвращая их освобождение ARC. Методы обнаружения:
1. Инструменты Xcode:
- Debug Memory Graph (кнопка с графом в нижней панели отладчика). Показывает визуальный граф объектов в памяти. Циклы отображаются как замкнутые связи. Позволяет сразу увидеть, какие объекты участвуют в цикле.
- Instruments → Leaks. Запустите профилирование для обнаружения утечек памяти в runtime.
2. Профилактика в коде:
-
Всегда используйте
[weak self]или[unowned self]в замыканиях, когдаselfможет удерживать это замыкание.class DataLoader { var onComplete: (() -> Void)? func loadData(completion: @escaping () -> Void) { self.onComplete = completion // ... загрузка } func setupHandler() { loadData { [weak self] in // Разрываем потенциальный цикл self?.handleData() } } } - Для паттерна делегата всегда объявляйте свойство делегата как
weak.protocol MyDelegate: AnyObject { ... } class MainClass { weak var delegate: MyDelegate? }
3. Дополнительная настройка:
- Включение Zombie Objects (в схеме → Diagnostics) помогает отловить обращение к уже освобождённому (deallocated) объекту, что может быть косвенным признаком проблем с памятью.