Intereting Posts
Увеличьте высоту UITextField при использовании Autolayout iPhone dev, NSDictionary, как сохранить полный Dict? Ошибки, компилирующие приложения командной строки в iOS Получение GPS-координат видео в рулоне камеры на iphone Как удалить предупреждение при создании пользовательских фреймворков ios? Перемещение объектов случайным образом по экрану с определенной скоростью ios создает программный запрос сертификата Кнопка в заголовке используется для ввода нового контроллера вида Как записывать видео с оверлейными изображениями с использованием системы Avfoundation TextView. Затухайте текст вверху, уходя с экрана, как в Star Wars Есть ли способ подкласса MKAnnotationView, используемый для синей точки MKUserLocation? Swift – получение всех типов замыканий и приведение в objc_block слабая цель собственности c управление памятью Реальные и iOS сохраняемые циклы Редактируемый выпуск прокрутки UIWebview

Почему мой NSArray освобождается?

Я пытаюсь понять автоматический подсчет ссылок, поскольку я исхожу из языка программирования высокого уровня (Python), и я работаю над проектом, который использует эту функцию Objective-C. У меня часто возникают проблемы с ARC, освобождающим объекты, которые мне нужны позже, но теперь у меня есть конкретный пример, на который, я надеюсь, я получу объяснение.

- (void) animateGun:(UIImageView *)gun withFilmStrip:(UIImage *)filmstrip{ NSMutableArray *frames = [[NSMutableArray alloc] init]; NSInteger framesno = filmstrip.size.width / gun_width; for (int x=0; x<framesno; x++){ CGImageRef cFrame = CGImageCreateWithImageInRect(filmstrip.CGImage, CGRectMake(x * gun_width, 0, gun_width, gun_height)); [frames addObject:[UIImage imageWithCGImage:cFrame]]; CGImageRelease(cFrame); } gun.image = [frames objectAtIndex:0]; gun.animationImages = frames; gun.animationDuration = .8; gun.animationRepeatCount = 1; [gun startAnimating]; dispatch_after(dispatch_time(DISPATCH_TIME_NOW,(arc4random() % 300)/100 * NSEC_PER_SEC), dispatch_get_current_queue(),^{ [self animateGun:leftGun withFilmStrip:[self getFilmStripForAction:gunShoot andTeam:nil withWeapon:nil]]; }); } 

Идея этого фрагмента кода проста: у меня есть (UIImageView*)gun который я анимация с изображениями, хранящимися в (NSMutableArray *)frames , в произвольные моменты времени. (UIImage *)filmstrip – это просто изображение, которое содержит все кадры, которые будут использоваться при анимации. Первая итерация анимации работает, но проблемы появляются на второй итерации, где я получаю -[UIImage _isResizable]: message sent to deallocated instance ... или -[UIImage _contentStretchInPixels]: message sent to deallocated instance ... или -[NSArrayI release]: message sent to deallocated instance ... Это происходит при

 gun.animationImages = frames; 

но я не понимаю, почему. Я не требую исправления для моей проблемы, но просто чтобы помочь мне понять, что здесь происходит. Благодарю.

ARC – это механизм, который устраняет необходимость вручную сохранять / освобождать объекты. Вот хороший сайт, который объясняет, как это работает: http://longweekendmobile.com/2011/09/07/objc-automatic-reference-counting-in-xcode-explained/

Попробуйте изменить «leftGun» для «gun». Я думаю, что это, вероятно, тот, который получает освобождение в какой-то момент, если вы используете его через ivar. В противном случае leftGun просто не входит в сферу действия.

Вот как это должно выглядеть:

В вашем файле .h:

 @property (nonatomic, strong) IBOutlet UIImageView *leftGun; 

В файле .m:

  dispatch_after(dispatch_time(DISPATCH_TIME_NOW,(arc4random() % 300)/100 * NSEC_PER_SEC), dispatch_get_current_queue(),^{ [self animateGun:gun withFilmStrip:[self getFilmStripForAction:gunShoot andTeam:nil withWeapon:nil]]; }); 

Кроме того, не совсем уверен, откуда происходит «gunShoot». Предполагается, что это перечисление?

РЕДАКТИРОВАТЬ

Добавлен пример того, как должно быть определено свойство leftGun . Причина использования свойства над ivar для целей управления памятью. Если вы хотите освободить или уничтожить объект, являющийся свойством, просто установите его на nil, и свойство позаботится о том, чтобы освободить объект, если он есть.

Вы можете предотвратить освобождение массива frames если вы отметите его как __block .

  __block NSMutableArray *frames = [NSMutableArray array]; 

см. «Тип хранения __block».