Утечка в NSMutableArray - PullRequest
       15

Утечка в NSMutableArray

1 голос
/ 28 июля 2011

Я вырывал свои волосы, пытаясь понять, почему это протекает.В моем файле .h у меня есть синтезированное свойство nonatomic, сохраненное NSMutableArray.В моем viewDidLoad я объявляю его как:

self.tableData = [[NSMutableArray alloc] init];
[self.tableData removeAllObjects];
fillData(self.tableData);

Во всем приложении я вызываю [self.tableData removeAllObjects], а затем снова заполняю его функцией fillData (self.tableData).Эта функция заполняет данные из набора статических строк C ++:

void fillData(NSMutableArray* list)
{
    for (set<string>::const_iterator itr = sortedData.begin(); itr != sortedData.end(); ++itr){
        [list addObject:[NSString stringWithFormat:@"%s", ((string)*itr).c_str()]];
    }
}

В моем методе dealloc я делаю:

[self.tableData removeAllObjects], [self.tableData release], tableData = nil;

Где я уронил мяч?Instruments говорит, что он находится в строке [list addObject ....].

Спасибо

Ответы [ 4 ]

4 голосов
/ 28 июля 2011
self.tableData = [[NSMutableArray alloc] init];
[self.tableData removeAllObjects];
fillData(self.tableData);

+ 1 сохранение для alloc, +1 сохранение для использования установщика свойства.Вы не уравняли +1 с alloc.Если вы собираетесь использовать сеттер:

self.tableData = [NSMutableArray array];
fillData(self.tableData);

Обратите внимание, что removeAllObjects в этом совершенно бессмысленно.

Это тоже странно:

[self.tableData removeAllObjects], [self.tableData release], tableData = nil;

Во-первых, не беспокойтесь об удалении объектов.Когда массив будет освобожден, он освободит все объекты.Во-вторых, использование сеттера для вызова release, а затем немедленное прямое назначение противоречиво.Либо выполните:

self.tableData = nil;

Или:

[tableData release], tableData = nil;

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

Также используйте stringWithUTF8String:, а не stringWithFormat:.

0 голосов
/ 28 июля 2011

В вашем dealloc вы используете свойства, которые снова сохраняют данные таблицы.Это не совсем то, что вам нужно, поэтому сделайте следующее:

[tableData release];

или

[self->tableData release]; // not necessary, but some prefer it.

или

self.tableData = nil; // property will handle release

Нет необходимости очищать данные таблицы, нет необходимостиустановите значение nil (вы освобождаете, так что ничто больше не получит к нему доступ).

0 голосов
/ 28 июля 2011

Проблема в том, что ваше свойство установлено как сохраняемое, а вы устанавливаете его для уже сохраненного объекта.Вы должны сделать это так:

// viewDidLoad
NSMutableArray *array = [[NSMutableArray alloc] init];
self.tableData = array;
[array release]; // this is important

// dealloc
self.tableData = nil; // will automatically release the array
0 голосов
/ 28 июля 2011

Не уверен, что это утечка , но похоже, что это проблема:

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

Вы говорите, что tableData это свойство, которое сохраняется. Попробуйте:

self.tableData = [NSMutableArray arrayWithCapacity:10];

Таким образом, свойство сохраняет его, а сам массив автоматически высвобождается. Ваш релиз в dealloc вернет счет удержания в ноль.

...