Я работаю в чистой среде iOS5 / ARC, поэтому при необходимости могу использовать __слабые ссылки. Во многих ситуациях я делаю ссылки на ivars в блоке, в частности, на блоки анимации, которые перемещают представления, которые являются свойствами, скажем, моего класса контроллера представления.
Мой вопрос:
При самом простом использовании ivars в блоке я создаю контрольный цикл? Нужно ли мне использовать технику __weak self / strong self каждый раз Я пишу блок, который манипулирует переменными экземпляра содержащего объекта?
Я пересматривал сессию WWDC 2011 года № 322 («Достижения Objective-C в глубине»), чтобы понять нюансы, касающиеся 3-минутного сегмента, начиная с индекса времени 25:03 о «Цикле отсчета через захваченное Я». Для меня это означает, что любое использование ivars в блоке должно быть защищено с помощью настройки слабого self / strong self, как описано в этом сегменте.
Пример метода ниже на контроллере представления типичен для анимации, которую я делаю.
В блоке openIris неправильно ли ссылаться на ивары «_topView» и «_bottomView», как у меня?
Должен ли я всегда устанавливать __слабую ссылку на себя перед блоком, затем сильную ссылку в блоке на слабую ссылку, заданную ранее, а затем обращаться к иварам через эту сильную ссылку в моем блоке?
Начиная с сессии WWDC, я понимаю, что ссылка на ivars в блоке действительно создает ссылку на подразумеваемое «я», от которого зависают эти ivars.
Для меня это означает, что на самом деле не существует ни одного простого или тривиального случая, когда правильно получить доступ к иварам в блоке без слабого / сильного танца, чтобы гарантировать отсутствие циклов. Или я читаю слишком много в угловом деле, которое не относится к простым случаям, таким как мой пример?
- (void)openIrisAnimated:(BOOL)animated
{
if (_isIrisOpened) {
NSLog(@"Asked to open an already open iris.");
return; // Bail
}
// Put the common work into a block.
// Note: “_topView” and “_bottomView” are the backing ivars of
// properties “topView” and “bottomView”
void (^openIris)() = ^{
_topView.frame = CGRectMake(....);
_bottomView.frame = CGRectMake(....);
};
// Now do the actual opening of the iris, whether animated or not:
if (animated) {
[UIView animateWithDuration:0.70f
animations:^{
openIris();
}];
}
else {
openIris();
}
_irisOpened = YES; // Because we have now just opened it
}
Вот как я переписал бы часть блока openIris, используя руководство из Сессии # 322, но мне просто интересно, требуется ли для всех моих подобных блоков этот слабый / сильный эталонный танец для обеспечения правильности и стабильности:
__weak MyClass *weakSelf = self;
void (^openIris)() = ^{
MyClass *strongSelf = weakSelf;
if (strongSelf) {
strongSelf.topView.frame = CGRectMake(....);
strongSelf.bottomView.frame = CGRectMake(....);
}
};
Действительно ли это необходимо?