我无法弄清楚为什么__weak引用self会在下一个块中消失。遵循Jiva的建议在这里找到 http://blog.random-ideas.net/?p=160我在完成块之外对self进行__weak引用,然后对块内的弱引用进行强引用,以便在块的持续时间内保持它。
我遇到的问题是,当块执行时弱引用(weakSelf)为零,但如果我只是在块中直接调用self,则一切正常。
- (void)fetchItemList:(NSArray *)itemList withHandler:(ItemFetchCompletion)completionHandler
{
NSString *fetchString = [self fetchRequestUsingItemList:itemList];
NSURL *fetchUrl = [NSURL URLWithString:fetchString];
ASIHTTPRequest *itemListRequest = [ASIHTTPRequest requestWithURL:fetchUrl];
__weak FetchManager *weakSelf = self;
__weak ASIHTTPRequest *itemListRequestWeakRef = itemListRequest;
[itemListRequest setCompletionBlock:^{
ASIHTTPRequest *itemListRequestStrongRef = itemListRequestWeakRef;
ZAssert(weakSelf, @"weakSelf reference is nil.");
FetchManager *strongSelf = weakSelf;
NSData *fetchedData = [itemListRequestStrongRef responseData];
NSArray *fetchedItems = [strongSelf itemsFromFetchedData:fetchedData];
completionHandler(fetchedItems);
}];
[itemListRequest startAsynchronous];
}
答案 0 :(得分:4)
这基本上是您的代码正在做的事情:
weakSelf
。此时,self
不会被块保留,也不会保留weakSelf
变量。然后,当块运行时,weakSelf
被放入__strong
变量,从而保留weakSelf
中的任何值。很遗憾,如果weakSelf
的原始值self
已经取消分配,则weakSelf
已经nil
。
编译器可以查看块访问的外部变量,然后在这些变量为__strong
时添加任何必要的保留。编译器并不关心您将__weak
变量分配给恰好为__strong
的内部变量。当块运行时,此保留将发生,而不是在创建时。
通过直接从块中使用self
,编译器会发现您引用的变量不是__weak
,因此会自动将该变量保留在块的生命周期中。在这种情况下,除非你担心循环保留周期,否则我认为没有理由不直接在块中引用self。