Объект Objective-C неожиданно освобождается - PullRequest
0 голосов
/ 05 февраля 2010

Я очень плохо знаком с Objective-C и пытаюсь разработать приложение для iPhone. Моя проблема заключается в том, что при использовании объекта внутри NSTimer я получаю сообщение об ошибке «сообщение отправлено на освобожденный экземпляр 0x3d54830» Когда я не использую NSTimer, я могу использовать объект просто отлично. Например:

//These can be any objects.  Le't say I have a Song class and a SongReader class in the header file SongTest.h
Song *song;
SongReader *reader;

NSTimer *timer;

- (void)justDoIt;


//In the implementation file SongTest.m
- (void)viewDidLoad {
    reader = [[SongReader alloc] init];
    song = [reader readSong];

    timer = [NSTimer scheduledTimerWithTimeInterval:1 target:self selector:@selector(justDoIt) userInfo:nil repeats:YES];
}

- (void)justDoIt {
    NSLog(@"This is a song integer property: %d", song.wordCount);
}

- (void)dealloc {
    [reader release];
    [super dealloc];
}

Объект песни внутри метода / селектора / сообщения justDoIt уже освобожден в соответствии с отладчиком. Что я делаю неправильно? Даже если я сделаю это так:

song = [[reader readSong] retain]; //or
[song retain]; //or
[reader retain];

Объект все еще неожиданно освобождается. Опять же, проблема возникает только тогда, когда я использую NSTimer. Это похоже на то, что объект освобождается даже до срабатывания таймера.

Ответы [ 3 ]

2 голосов
/ 05 февраля 2010

Проблема может быть целью вызова NSTimer (то есть "себя"). Таким образом, сообщение «justDoIt» отправляется в освобожденный экземпляр, объект, представленный в вашем коде как «self»

Освобожден ли экземпляр контроллера до срабатывания таймера?

1 голос
/ 05 февраля 2010

Вы сохраняете свой объект SongTest? Вы не показываете эту часть кода, но если она автоматически освобождена, она будет освобождена к моменту срабатывания таймера. На самом деле, именно это и указывает сообщение об ошибке:

"сообщение отправлено на освобожденный экземпляр 0x3d54830"

Вы создаете таймер для отправки сообщения "self", которое является объектом SongTest.

Кроме того, вам нужно сохранить песню:

song = [[reader readSong] retain];

если вы кодировали -readSong в соответствии со стандартными соглашениями о какао.

0 голосов
/ 06 февраля 2010

Вы должны использовать свойства, чтобы предотвратить появление подобных ошибок. Если вы определяете песню как ...

@property(nonatomic, retain)  Song *song;
...
@synthesize song;

... и используйте его вот так ...

self.song = [читатель читает песню];

... target-c управляет удержанием и освобождением для вас, пока вы не вызовете dealloc.

Не связанная с вами основная проблема, метод, вызываемый таймером, должен иметь вид ...

-(void) arbitraryMethodName:(NSTimer *) aTimer;

... или это не всегда может быть вызвано должным образом.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...