__weak 和 __block 引用有什么区别? [英] What is the difference between a __weak and a __block reference?

查看:21
本文介绍了__weak 和 __block 引用有什么区别?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在阅读 Xcode 的文档,这里有一些让我感到困惑的东西:

I'm reading Xcode's documentation, and here is something that puzzles me:

__block typeof(self) tmpSelf = self;
[self methodThatTakesABlock:^ {
    [tmpSelf doSomething];
}];

以下内容是从文档中复制的:

The following is copied from the documentation:

块形成对其捕获的变量的强引用.如果你使用self 在块内,块形成对 self 的强引用,所以如果self 也有一个对块的强引用(它通常确实),强引用循环结果.为了避免循环,你需要在块外创建一个对 self 的弱(或 __block)引用,如在上面的例子中.

A block forms a strong reference to variables it captures. If you use self within a block, the block forms a strong reference to self, so if self also has a strong reference to the block (which it typically does), a strong reference cycle results. To avoid the cycle, you need to create a weak (or __block) reference to self outside the block, as in the example above.

我不明白弱(或__block)"是什么意思?

I don't understand what does 'a weak (or __block)' mean?

__block typeof(self) tmpSelf = self;

__weak typeof(self) tmpSelf = self;

这里完全一样吗?

我在文档中发现了另一篇文章:

I found another piece in the document:

注意:在垃圾收集环境中,如果同时应用 __weak__block 修饰符给一个变量,那么这个块就不能保证它是存活的.

Note: In a garbage-collected environment, if you apply both __weak and __block modifiers to a variable, then the block will not ensure that it is kept alive.

所以,我完全不解.

推荐答案

来自关于 __block 的文档

From the docs about __block

__block 变量存在于变量的词法范围和在变量词法范围内声明或创建的所有块和块副本之间共享的存储中.因此,如果在帧内声明的块的任何副本在帧结束后仍然存在(例如,通过排队等待稍后执行),则存储将在堆栈帧被破坏后继续存在.给定词法范围内的多个块可以同时使用一个共享变量.

__block variables live in storage that is shared between the lexical scope of the variable and all blocks and block copies declared or created within the variable’s lexical scope. Thus, the storage will survive the destruction of the stack frame if any copies of the blocks declared within the frame survive beyond the end of the frame (for example, by being enqueued somewhere for later execution). Multiple blocks in a given lexical scope can simultaneously use a shared variable.

来自关于 __weak 的文档

From the docs about __weak

__weak 指定一个引用,它不会使被引用的对象保持活动状态.当对象没有强引用时,弱引用设置为 nil.

__weak specifies a reference that does not keep the referenced object alive. A weak reference is set to nil when there are no strong references to the object.

所以它们在技术上是不同的东西.__block 是为了阻止你的变量从你的外部作用域复制到你的块作用域中.__weak 是一个自定界的弱指针.

So they are technically different things. __block is to stop your variable being copied from your external scope into your block scope. __weak is a self delimiting weak pointer.

注意我说的是技术上的,因为对于你的情况,他们会(几乎)做同样的事情.唯一的区别是您是否使用 ARC.如果你的项目使用 ARC 并且仅适用于 iOS4.3 及以上版本,请使用 __weak.如果全局范围引用以某种方式释放,它确保引用设置为 nil.如果您的项目不使用 ARC 或用于较旧的操作系统版本,请使用 __block.

Note I said technically, because for your case they will do (almost) the same thing. The only difference is if you are using ARC or not. If your project uses ARC and is only for iOS4.3 and above, use __weak. It ensures the reference is set to nil if the global scope reference is releases somehow. If your project doesn't use ARC or is for older OS versions, use __block.

这里有一个微妙的区别,确保你理解它.

There is a subtle difference here, make sure you understand it.

另一个难题是 __unsafe_unretained.此修饰符几乎与 __weak 相同,但适用于 4.3 之前的运行时环境.但是,它没有设置为 nil 并且可能会给您留下悬垂的指针.

Another piece to the puzzle is __unsafe_unretained. This modifier is almost the same as __weak but for pre 4.3 runtime environments. HOWEVER, it is not set to nil and can leave you with hanging pointers.

这篇关于__weak 和 __block 引用有什么区别?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

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