Avoid block circular references what is a circular reference, when a circular reference occurs
1 A circular reference is when self has a block, and the method of self is called at block. Form you have me, I have you, who can not release who the dilemma.
self.myBlock = ^{ [self doSomething]; }; +-----------+ +-----------+ | self | | Block | ---> | | --------> | | | retain 2 | <-------- | retain 1 | | | | | +-----------+ +-----------+
Or
ClassA* objA = [[[ClassA alloc] init] autorelease]; objA.myBlock = ^{ [self doSomething]; }; self.objA = objA; +-----------+ +-----------+ +-----------+ | self | | objA | | Block | | | --------> | | --------> | | | retain 1 | | retain 1 | | retain 1 | | | | | | | +-----------+ +-----------+ +-----------+ ^ | | | +------------------------------------------------+
This is the official explanation at the time.
The general meaning is that, for example, Self has a button, and you have to invoke something in the button setting.
[self.button ^{ }]
So far, there's no problem, but for some reason, you're going to call it in this block again.
Self.label.text = @ "I am Label";
That's it.
[self.button ^{ self.label.text = @"I am Label"; }];//这个时候就变成这样了。 +-----------+ +-----------+ +-----------+ | self | | button | | Block | | | --------> | | --------> | | | retain 1 | | retain 1 | | retain 1 | | | | | | | +-----------+ +-----------+ +-----------+ ^ | | | +------------------------------------------------+
The general understanding is this, if there are deviations, please point out.
Workaround
In short, just one sentence:
__weak typeof (self) weakSelf = self;
For example, the above example, as follows.
__weak typeof (self) weakSelf = self;[self.button ^{ weakSelf.label.text = @"I am Label"; }];//这个时候就变成这样了。 +-----------+ +-----------+ +-----------+ | self | | button | | Block | | | --------> | | --------> | | | retain 1 | | retain 1 | | retain 1 | | | | | | | +-----------+ +-----------+ +-----------+ ^ | | | + - - - - - - - - - - - - - - - - - - - - - - - -+ weak
Avoid a circular reference to a block