UIAdam 给出了正确的答案,但值得理解为什么它是正确的。
首先,您为什么收到警告?
self 对 webClient 有很强的引用。webClient 对 completionHandler 有很强的引用。completionHandler 对 self 有很强的引用。因此,如果您的程序中的所有其他引用都消失了,那么在这个循环中仍然存在对每个项目的强引用,因此它们永远不会被释放。
写作的尝试
__weak id myself = self;
[myself populateData];
当然不起作用。该块仍然引用自我,因为它正在将它分配给我自己。所以这里没有区别。
UIAdam 的写作解决方案
__weak id 弱自我 = 自我;self.webClient.completionHandler = ^{ [weakSelf populateData]; };
表示weakSelf是一个弱引用,block只包含一个对self的弱引用。因此,如果所有其他对 self 的强引用都消失了,则只剩下一个弱引用。弱引用不会使 self 保持活动状态,因此 self 会被释放。
现在如果发生这种情况,但是其他东西对 webClient 有很强的引用并且你的块被调用了怎么办?weakSelf 是一个弱引用,当对象被释放时,弱引用被设置为 nil。所以你必须做好准备,当你的块被调用时,weakSelf 为零。实际上写得更好
id strongSelf = weakSelf;
[strongSelf populatedData];
块内部:strongSelf 可能设置为 nil,或者将设置为 self。但由于它是一个强引用,所以在块完成之前它将保持非零。如果它不是零开始的。