I think I understand how simple retain cycles are create but I don't fully understand more complicated situations.
Here is code that would cause a retain cycle. (right?)
[self.dataController loadInitialWithCompletion:^(BOOL dataChanged) {
self.loading = NO;
}];
To avoid that retain cycle I would create a weak reference to self
:
__weak typeof(self) welf = self;
[self.dataController loadInitialWithCompletion:^(BOOL dataChanged) {
welf.loading = NO;
}];
I hope I'm correct so far.
Here's where it gets interesting. I have a method that calculates and caches text heights and then calls reloadData on a tableView. That method executes asynchronously and calls it's completionBlock (on the mainThread) when it's finished.
__weak typeof(self) welf = self;
[self.dataController loadInitialWithCompletion:^(BOOL dataChanged) {
[welf relayoutWithCompletion:^(CGPoint offsetBeforeReload) {
welf.loading = NO;
if (dataChanged) {
[welf save];
}
}];
}];
Will this code cause a retain cycle because welf
captures itself in the completionBlock for relayoutWithCompletion:
? Am I correct in thinking that because welf is a weak reference I will avoid a retain cycle?
What if I took it a step further?
__weak typeof(self) welf = self;
[self.dataController loadInitialWithCompletion:^(BOOL dataChanged) {
[welf relayoutWithCompletion:^(CGPoint offsetBeforeReload) {
if (offsetBeforeReload.y > 64) {
[welf scrollToPoint:offsetBeforeReload completion:^{
welf.loading = NO;
[welf save];
}];
}
}];
}];
It's welf all the way down...