What does it mean when a variable is both __block and __weak in ARC?
我知道弧中的块保留了变量。然后,可以在分配变量之前访问块内的变量,如:
1 2 3 4 5 | __block __weak id observer = [[NSNotificationCenter defaultCenter] addObserverForName:MPMoviePlayerPlaybackDidFinishNotification object:player queue:[NSOperationQueue mainQueue] usingBlock:^(NSNotification* notif){ // reference the observer here. observer also retains this block, // so we'd have a retain cycle unless we either nil out observer here OR // unless we use __weak in addition to __block. But what does the latter mean? }]; |
但我在分析这个问题上遇到了困难。如果
在您的示例中,observer捕获addobserverforname:object:queue:usingblock:的返回值,因此它不需要很强。如果它是强的,那么它就保留了观察者,使其成为全球性的,并一直存在,直到强引用被设置为零。
例子
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 | #import <Foundation/Foundation.h> void (^foo()) () { NSString* str= [[NSString alloc]initWithFormat: @"Hey"]; __block __weak NSString* x= str; return ^ { NSLog(@"%@",x); }; } int main(int argc, char** argv) { @autoreleasepool { void (^block) ()= foo(); block(); } return 0; } |
此示例打印(空),让我们看看发生了什么:
- 字符串@"hey"的弧参考计数为1;
- 它在块中使用,但由于它很弱,不能被块保留,所以它的计数仍然为1;
- 返回并执行块,因为我们从foo函数作用域退出,字符串被释放,指针x被设置为nil。
所以你可以这样做:
1 2 3 4 5 6 7 8 | void (^foo()) () { NSString* str= [[NSString alloc]initWithFormat: @"Hey"]; return ^ { NSLog(@"%@",str); }; } |
没有问题:str在默认情况下是强的,所以它是被捕获的,您不需要uu块说明符。