Ответ
Чтобы избежать увеличения счетчика сильных ссылок, нужно использовать коллекции, хранящие weak (слабые) или unowned ссылки. В чистом Swift для этого нужна специальная обертка.
Решение: Обертка Weak
class Weak<Object: AnyObject> {
weak var value: Object?
init(_ value: Object) {
self.value = value
}
}
// Использование
class MyClass {}
var weakContainer = [Weak<MyClass>]()
let object = MyClass()
weakContainer.append(Weak(object)) // Счетчик сильных ссылок на object НЕ увеличивается.
// При обращении нужно учитывать, что значение может стать nil
for weakRef in weakContainer {
if let object = weakRef.value {
// Работаем с object
}
}
Альтернативы и примечания:
NSPointerArray(из Objective-C): Может быть сконфигурирован для хранения weak-указателей.NSHashTable/NSMapTable: Foundation-коллекции с опциями хранения weak-объектов.- Слабые ссылки автоматически обнуляются (
nil), когда объект освобождается. Это необходимо всегда проверять перед использованием. - Такой подход часто используется для реализаций паттернов вроде observer/listener, чтобы избежать циклов retain-ов.