栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 面试经验 > 面试问答

快速闭合导致自我强烈的保留周期

面试问答 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

快速闭合导致自我强烈的保留周期

是的,那仍然会导致保留周期。

最简单的保留周期是2个对象,每个对象相互之间都有很强的引用,但是3向和更大的保留周期也是可能的。

在您的情况下,您的视图控制器的视图包含一个按钮(强引用)。该按钮具有对闭包的强引用。闭包使用self强烈引用视图控制器。因此,视图拥有该按钮。该按钮拥有闭包。该闭包拥有视图控制器。如果您关闭视图控制器(例如它是模式控制器),则应该将其释放。但是,由于您具有此3向保留周期,因此不会取消分配它。您应该使用打印语句将deinit方法添加到视图控制器,然后尝试使用它。

解决方案是

[weak self]
像在第一个示例中那样添加捕获列表(该位)。

请注意,常见的模式是添加捕获列表,然后将弱变量映射到闭包内部的强变量:

let myClosure = { [weak self] in   guard let strongSelf = self else { return }  //...  strongSelf.doSomething()}

这样,如果闭包仍处于活动状态,但拥有它的对象已被释放,则开始时的guard语句会检测到self为nil,并在闭包的开头退出。否则,每次引用可选项时都必须将其拆开。

在某些情况下,捕获列表中的对象(在这些示例中为self)也有可能被释放到正在执行的闭包的中间,这可能导致无法预测的行为。(详细信息:仅当闭包在与捕获列表中对象的所有者不同的线程上运行时,但完成处理程序通常在后台线程上运行,因此确实发生)

想象一下:

let myClosure = { [weak self] in  self?.step1() //1  //time-consuming pre  self?.property = newValue //2  //more time-consuming pre  self?.doSomething() //3  //even more time-consuming pre  self?.doSomethingElse() //4}

使用上面的代码,如果闭包在后台线程上运行,则可能在第1步中self仍然有效,但是到您执行第2步时,self已被释放。步骤3和步骤4也是如此。通过

guardstrongSelf = self else { return}
在闭包的开头添加,您可以在闭包的入口处进行测试以确保self仍然有效,如果是,则使闭包创建一个仅能生存的强引用。只要闭包需要运行,并且可以防止
self
在执行闭包代码时将其释放。)



转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/413217.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号