可以在没有__weak对象的块中传递[self anyFunction](iOS 5 + ARC) [英] Possible to pass [self anyFunction] in blocks without __weak object (iOS 5 + ARC)

查看:115
本文介绍了可以在没有__weak对象的块中传递[self anyFunction](iOS 5 + ARC)的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

是否可以在没有__weak对象的块中传递[self anyFunction]?



作为示例,这是来自系统框架的有效代码:

  [UIView animateWithDuration:0.8动画:^ {
//执行animationStuff
}完成:^(BOOL完成){
[self anyFunction];
}];

您可以传递 [self anyFunction] in没有警告的完成块。但如果您使用完成块编写自己的方法,则会出现以下警告:在此块中强烈捕获自我可能会导致保留周期



工作解决方案非常简单(iOS 5 + ARC)。在块声明之前:

  __弱MyClass * weakSelf = self; 

在完成区块中你必须致电:

  [weakSelf anyFunction]; 

但是,回到我的问题:为什么系统框架API中不需要使用 __弱对象并使用 self ,没有任何警告。如何实现一个方法而不需要块中的 __弱对象?



谢谢你的努力。

解决方案

抛出错误的块是你捕获拥有的对象的块

块。例如

  [object performBlock:^ {
[object performSomeAction]; //会发出警告
}];

  [self performBlock:^ {
[self doSomething]; //会发出警告
}];

但是

  [self performBlock:^ {
[object doSomething]; //< - 这里没问题
}];

因为一个对象保留了它的块,一个块保留了它的对象。因此,在这两种情况下,执行块的对象拥有块,该块也拥有该对象。所以你有一个循环 - 一个保留周期。这意味着内存已泄露。



在您给出的示例中 - 您正在查看类方法。您在 UIView 类上调用该块,而不是 UIView 对象。类没有与之关联的内存。你可能正在从控制器调用这个函数,所以块保留了 self 引用,但是没有循环,因为self没有保留块。



就像你可能已经注意到的那样,并非所有在块中使用的对象都需要被弱引用 - 只是导致保留周期的对象。


Is it possible to pass [self anyFunction] in blocks without a __weak object from self?

As an example this is valid code from the System Framework:

[UIView animateWithDuration:0.8 animations:^{
            //Do animationStuff
        } completion:^(BOOL finished) {
            [self anyFunction];
 }];

You can pass [self anyFunction] in the completion block without a warning. But if you write your own method with a completion block, the following warning occurs: capturing 'self' strongly in this block is likely to lead to a retain cycle.

A working solution is quite simple (iOS 5 + ARC). Before the block declare:

__weak MyClass *weakSelf = self;

and in the completion block you have to call:

[weakSelf anyFunction];

But, back to my Question: Why there is no need in the System Framework APIs to use a __weak object and to use self without any warnings. And how to implement a method without the need of a __weak object in the block?

Thank you for your effort.

解决方案

The blocks which throw up the error are ones where you capture the objects that own the block. For example

[object performBlock:^{
    [object performSomeAction]; // Will raise a warning
}];

or

[self performBlock:^{
    [self doSomething];    // Will raise a warning
}];

but

[self performBlock:^{
    [object doSomething];    // <-- No problem here
}];   

Because an object retains its blocks, and a block retains it's objects. So in both these cases, the object which performs the block owns the block, which also owns the object. So you have a loop - a retain cycle. which means the memory is leaked.

In the example you have given - you're looking at a class method. You're calling the block on a UIView class, not a UIView object. A class has no memory associated with it. And you are probably calling this function from a controller, so the self reference is being retained by the block, but there is no loop because self is not retaining the block.

In the same way that, you may have noticed, not all objects that are used in the block need to be weakly referenced - just the ones that cause a retain cycle.

这篇关于可以在没有__weak对象的块中传递[self anyFunction](iOS 5 + ARC)的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

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