Почему этот код Objective C утечка памяти? - PullRequest
3 голосов
/ 30 ноября 2010

Почему эта утечка?

arrayOfPerformances - это свойство NSMutableArray, (nonatomic, retain), которое синтезируется.

currentPerformanceObject - это синтезированное свойство Performance *, (nonatomic, retain).

Performance - это пользовательский класс

if(self.arrayOfPerformances == nil)
    {
        self.arrayOfPerformances = [[NSMutableArray alloc]init];
    }

    [self.arrayOfPerformances addObject:currentPerformanceObject];
    [currentPerformanceObject release];
    currentPerformanceObject = nil;

Ответы [ 3 ]

11 голосов
/ 30 ноября 2010

Вы создаете новый массив и , сохраняя его одновременно в этой строке, потому что вы вызываете установщик свойства (retain) с точечной нотацией:

// Your property
@property (nonatomic, retain) NSMutableArray *arrayOfPerformances;

// The offending code
self.arrayOfPerformances = [[NSMutableArray alloc]init];

Из-за этого локально созданный массив протекает, потому что вы его не освобождаете.Вы должны автоматически освободить этот массив или создать временную локальную переменную, назначить, а затем освободить локальную переменную следующим образом:

// Either this
self.arrayOfPerformances = [[[NSMutableArray alloc] init] autorelease];

// Or this (props Nick Forge, does the same as above)
self.arrayOfPerformances = [NSMutableArray array];

// Or this
NSMutableArray *newArray = [[NSMutableArray alloc] init];
self.arrayOfPerformances = newArray;
[newArray release];
4 голосов
/ 30 ноября 2010

Если ваше свойство .arrayOfPerformances никогда не освобождается (обычно оно высвобождается в -dealloc), тогда сам массив, а также любой объект в массиве будет вытекать при освобождении этого объекта.Вам нужно освободить оба свойства в вашем -dealloc:

- (void)dealloc
{
    ... other deallocs
    self.arrayOfPerformances = nil;
    self.currentPerformanceObject = nil;
    [super dealloc];
}

Кроме того, как указывало @BoltClock, вам нужно освободить или автоматически разблокировать NSMutableArray.Лучший способ сделать это - инициализировать его, используя метод автоматического освобождения:

self.arrayOfPerformances = [NSMutableArray array];

Кроме того, вам не нужно выпускать currentPerformanceObject, вам просто нужно установить свойство равным nil, так как установкаretain ed свойство для nil выпустит его для вас.Ваш код должен выглядеть примерно так:

if (self.arrayOfPerformances == nil) {
    self.arrayOfPerformances = [NSMutableArray array];
}
[self.arrayOfPerformances addObject:self.currentPerformanceObject];
self.currentPerformanceObject = nil;
1 голос
/ 30 ноября 2010

Эта строка является виновником:

self.arrayOfPerformances = [[NSMutableArray alloc]init];

Число сохраненных единиц - 1 после выделения / инициализации. Установка значения с помощью установщика свойства arrayOfPerformances снова увеличивает счет сохранения (поскольку это свойство сохранения).

...