在块中强引用,会保留吗? [英] Strong reference in the block, it will be retained?

查看:75
本文介绍了在块中强引用,会保留吗?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我从公司的文档中发现了以下代码段:

I discover this snippet code from company's document:

__weak __typeof(self)weakSelf = self;
dispatch_async(dispatch_get_main_queue(),
^{
      __strong __typeof(weakSelf)strongSelf = weakSelf; 
      // Do stuff
});

它会保留吗?

推荐答案

在块内捕获weak引用有两个原因.

There are two reasons to capture weak references within a block.

  1. 避免保留周期

  1. avoid retain cycles

创建无操作情况.

前者已经被讨论过.第二个更有趣.

The former has been discussed ad-nauseum. The second is more interesting.

示例

所讨论的块是图像下载的完成处理程序.下载完成后,它将显示在图像视图中.

The block in question is a completion handler for an image download. When the download is complete, it is to be displayed in an image view.

如果图像视图已被重新分配(例如,用户已切换到新视图),则无需执行任何操作.没有保留周期的危险,因为图像视图没有引用该块.但是,捕获weak引用允许在块执行之前重新分配图像视图.因此,如果用户在下载图像之前切换视图,则该块最终将不执行任何操作,因为其weak引用已被nil引用.图像视图是否在块的执行过程中被重新分配也无关紧要,因为它只是将对图像视图的操作变为无操作,而不是将整个块变为无操作.

It doesn't need to do anything if the image view has already been deallocated (say the user has switched to a new view). There is no danger of a retain cycle, because the image view has no reference to the block. However, capturing a weak reference allows the image view to be deallocated before the block executes. Thus, if the user switches views before the image is downloaded, the block ends up doing nothing because its weak reference has already been niled. It also doesn't matter if the image view is deallocated part way through the block's execution, because it just turns operations on the image view into no-ops, instead of turning the entire block into a no-op.

但是,有时,该块希望无操作行为,但前提是引用开始时(或到达代码路径中的特定点)已经是nil.如果在执行该块时该对象处于活动状态,则该块必须全部执行.它无法中途停止,因为该对象已被释放到其他线程上.

Sometimes, however, the block wants the no-op behavior, but only if the reference was already nil when it began (or reached a certain point in the code path). If, at the time the block executes, the object is live, the block has to execute in its entirety. It can't stop half-way through because the object is deallocated on some other thread.

示例

完成块的目的是向图像添加由字符串定义的标题.如果字符串已经被释放,则不添加标题.但是,如果字符串在后期处理开始时仍处于活动状态,则必须保持活动状态,以避免尝试使用nil引用创建属性字符串,因为这会导致崩溃.

The purpose of the completion block is to add a caption, defined by a string, to the image. If the string has been deallocated already, no caption is to be added. However, if the string is still live when post-processing begins, it must remain live to avoid trying to create an attributed string with a nil reference, because that leads to a crash.

在这种情况下,使用weak引用捕获字符串是适当的,因此可以由其他某个线程将其释放(不带标题).但是,在块中使用字符串之前,必须strong ly对其进行捕获,以避免在创建属性字符串时发生崩溃.

In this scenario, it would be proper to capture the string with a weak reference, so it can be deallocated by some other thread (leading to no caption). However, before the string is used within the block, it must be captured strongly to avoid a crash when creating the attributed string.

这篇关于在块中强引用,会保留吗?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆