Почему в GameCenterManager.m есть утечка памяти? - PullRequest
0 голосов
/ 20 марта 2012

Я использую Game Center в своем приложении и обнаружил, что файл gamecentermanager.m вызывает утечку памяти:

- (void) callDelegate: (SEL) selector withArg: (id) arg error: (NSError*) err
{
assert([NSThread isMainThread]);
if([delegate respondsToSelector: selector])
{
    if(arg != NULL)
    {
        [delegate performSelector: selector withObject: arg withObject: err];
    }
    else
    {
        [delegate performSelector: selector withObject: err];
    }
}
else
{
    NSLog(@"Missed Method");
}
}

Утечка происходит (в соответствии с предупреждающими треугольниками компилятора), поскольку executeSelector (оба) селектор неизвестен.Есть 2 вещи, которые я хочу знать

1) Я скопировал это прямо из примера на веб-сайте Apple, поэтому не будет ли код не отображать ошибку, если Apple его построит?

2)Как я могу это исправить?

Так же, как к вашему сведению, я использую Xcode 4.3.1, используя LLMV Compiler 3.1 и стандартную (armv7) архитектуру.Я также использую ARC.

Если вам нужна какая-либо другая информация, просто дайте мне знать и поблагодарить вас заранее.

1 Ответ

1 голос
/ 20 марта 2012

Проблема в том, что ARC не может определить семантику управления памятью для метода, который вы вызываете с -performSelector:withObject:. В случае MRR это не имело значения, поскольку ожидалось, что вызывающий код будет соответствующим образом иметь с ним дело (например, путем освобождения возвращаемого значения, если это был принадлежащий объект). Но в ARC компилятору необходимо , чтобы знать, что эта информация верна. Я не помню, как по умолчанию он работает с -performSelector:withObject:, возможно, он просто обрабатывается как не принадлежащая ссылка, и в этом случае вы на самом деле не пропускаете.

Самый простой способ справиться с такого рода шаблоном делегата - это по-прежнему использовать -respondsToSelector:, а затем просто вызывать метод напрямую, например,

if ([_delegate respondsToSelector:@selector(foo:)]) {
    [_delegate foo:self];
}

В вашем случае сам метод на самом деле не знает, что такое селектор. Лучше всего, вероятно, полностью отказаться от этого метода и позволить его бывшим посетителям разобраться с делегатом.

...