С ARC, как правильно установить свойство с побочным эффектом? - PullRequest
4 голосов
/ 09 ноября 2011

У меня есть класс, который использует автоматический подсчет ссылок.В классе у меня есть свойство, как описано ниже.Когда я устанавливаю напоминание для класса, я хочу, чтобы побочный эффект изменения заголовка кнопки имел место.

Вот мой код:

в файле .h:

@property(nonatomic,strong)Reminder* reminder;

в файле .m: @synthesize напоминание;

  -(void)setReminder:(Reminder *)reminder_
    {
//what else do I need to do here?
        reminder = reminder_;
         if(!reminder.useSound.boolValue)
        {
             onOffButton.title = NSLocalizedString(@"Off", @"Off title");

        }else
        {
            onOffButton.title = NSLocalizedString(@"On", @"On title");
        }
    }

Я знаю, что без ARC я бы сделал что-то вроде этого:

-(void)setReminder:(Reminder *)reminder_

{

[reminder release];
reminder = [reminder_ retain];


     if(!reminder.useSound.boolValue)
    {
         onOffButton.title = NSLocalizedString(@"Off", @"Off title");

    }else
    {
        onOffButton.title = NSLocalizedString(@"On", @"On title");
    }
}

Нужно ли мне делать что-то еще в моем методе установки с поддержкой ARC, чтобы гарантировать, что сильная переменная сохраняется правильно?

1 Ответ

5 голосов
/ 09 ноября 2011

Вам не нужно писать свой собственный сеттер для таких побочных эффектов.Используйте KVO !

Заставьте контроллер, которому принадлежит кнопка, наблюдать свойство reminder этого объекта:

[reminderOwner addObserver:self
                forKeyPath:@"reminder"
                   options:NSKeyValueObservingOptionNew
                   context:NULL];

Аргумент options указывает, какую информацию о состоянии наблюдаемого объекта вы хотели бы передать при выполнении наблюдения.

Тогда ваш контроллер будет информироваться, когда это свойство изменяет значение (обратите внимание, что это произойдет, только если свойствоустанавливается в соответствии с ключом-значением, наиболее удобный способ - через метод setter - прямое изменение ивара не считается).

Вам необходимо реализовать observeValueForKeyPath:ofObject:change:context: в вашем контроллере:

- (void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary *)change context:(void *)context
{
    // Distinguish between observations if necessary; you can also
    // use the |object| argument for this.
    if( [keyPath isEqualToString:@"reminder"] ){
        // Update button text with contents of |change| dictionary
        Reminder * reminder = [change objectForKey:NSKeyValueChangeNewKey];
        if(!reminder.useSound.boolValue)
        {
             onOffButton.title = NSLocalizedString(@"Off", @"Off title");

        }else
        {
            onOffButton.title = NSLocalizedString(@"On", @"On title");
        }
    }
}

О, и чтобы ответить на ваш настоящий вопрос, я считаю, что с вашим управлением памятью все в порядке.reminder синтезируется как __strong -качественная переменная, что означает, что ARC сохранит все, что вы там поместили.


* Вот почему вы слышали, что в init не используются сеттерыи dealloc.

...