ios - 保留循环 Swift 闭包

标签 ios swift generics mvvm key-value-observing

我正在考虑使用这种模式(或类似模式)来观察纯 Swift 对象的变化。

这段代码是否有内存泄漏?

class Person {

   var name: String {
       didSet{
           self.listen?(self)
       }
   }

   var phone: Int {
       didSet{
           self.listen?(self)
       }
   }

   var listen: ((_ person: Person) -> Void)?

   init(withName N: String, andPhone P: Int) {
       self.name = N
       self.phone = P
   }
}

 class HouseHold {

   var people = [Person]()

   let changes: (_ person: Person) -> Void = { person in
       print(person.name)
   }

   init(withPeople P: [Person]){
       self.people = P
       for person in people {
           person.listen = self.changes
       }
   }
}

let jon = Person(withName: "Jon", andPhone: 1232344567)


let thais = Person(withName: "Thais", andPhone: 1232344567)


let apartment = HouseHold(withPeople: [jon, thais])

jon.phone = 1232399999
jon.name = "Jon Smith"
jon.phone = 9999999999
thais.name = "Thais Smith"

此外,假设我有一个 UIViewController 而不是 HouseHold,它以相同的方式监听来自 Person 对象的更改。会不会有内存泄漏?

此外,欢迎对模式发表评论。我很乐意使用泛型,这样我就不必为我想观察的每个属性都创建一个函数。或者像代码当前那样传递整个对象。

注意:在 Playground 上编译

注意 2:尝试在不使用 reactive cocoa 的情况下迁移到更多 MVVM 架构。

最佳答案

您的代码没有保留周期。因为:

HouseHold has Person, HouseHold has changes, Person has HouseHold.changes. 

上面没有Cycle。

如果您的代码更改为:

,则会发生循环
person.listen = self

情况是:

HouseHold has Person, Person has HouseHold. 

您可以通过检查 deinit 方法来测试泄漏:

class Person {

    //...

    deinit {
        print("Person deinited")
    }
}

class HouseHold {

    //...

    deinit {
        print("HouseHold deinited")
    }
}

关于ios - 保留循环 Swift 闭包,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/44018581/

相关文章:

ios - 在前台推送通知

ios - for 语句循环未按预期工作

swift - 检测 iMessage 扩展中的用户交互

ios - 如何在 MobileVLCKit 中设置循环视频?

swift - 有没有办法在 RealityKit 中将 View 渲染为实体?

ios - 如何正确旋转 map 上的叠加层?

ios - 带均衡器的 AVPlayer

java - 带有 List<String> 的原始类型给出编译错误

java - 填充用 <?> 类型声明的数组

Java 泛型类型实例化