Мой код либо утекает и работает, либо не утекает и вылетает. Это не похоже на проблему с автоматическим выпуском
-
07-07-2019 - |
Вопрос
После того, как я закончил кодировать сложные части моей игры, я обнаружил некоторые ошибки управления памятью. Р>
objects - это NSMutableArray, содержащий пользовательский класс. Р>
- (void) spawnObjects
{
for (int index = 0; index < INITIAL_OBJECTS; index++)
{
[objects addObject:[[[MatchObject alloc] initWithImageNameID:(index % 3)] autorelease]];
[[objects objectAtIndex:index] setPosition:[GameLayer randomPoint]];
}
...
}
Позже я использую эту функцию.
- (void) checkAllSprites
{
NSMutableArray *spritesToDelete = [NSMutableArray array];
for (int index = 0; index < [points count] - 1; index ++)
{
for (MatchObject *planetLike in objects)
{
CGPoint point1 = [[points objectAtIndex:index] CGPointValue];
CGPoint point2 = [[points objectAtIndex:index+1] CGPointValue];
if ([GameLayer lineIntersectsCircle:point1 :point2 :[planetLike position] :16.0f])
{
ParticleSystem *planetDeath = [ParticlePlanetDeath node];
planetDeath.texture = [[TextureMgr sharedTextureMgr] addImage:@"fire.pvr"];
planetDeath.position = [planetLike position];
[self addChild:planetDeath z:0 tag:2];
[spritesToDelete addObject:planetLike];
[self removeChild:planetLike cleanup:YES];
}
}
}
[objects removeObjectsInArray:spritesToDelete];
[spritesToDelete removeAllObjects];
}
Если я не делаю авто-релиз в первой функции, приложение работает нормально. Если я это сделаю, то я пытаюсь получить доступ к освобожденному объекту ([MatchObject position]). Р>
Что не так?!
Решение
Похоже, вы ссылаетесь на освобожденную память. Когда вы действительно освобождаете память, она падает, потому что ваша программа освобождает память. Когда вы не освобождаете его с помощью автоматического выпуска, он все равно работает, потому что, несмотря на утечку памяти, система не замечает этого, поскольку объект фактически не освобожден, поэтому ссылка на него не вызывает проблем. р>
Итак, вытащите увеличительное стекло, снова посмотрите код и начните использовать отладчик ... получайте удовольствие :)
Другие советы
Просто дикая догадка:
Я полагаю, addChild сохраняет объект, а removeChild освобождает объект. Р>
Но что происходит, когда removeChild не находит объект (то есть, если он не дочерний)? Это освобождает объект тоже в этом случае? (чего не должно быть)
Любой шанс, что вы что-то делаете в " removeChild " метод, который в конечном итоге освобождает объект? Похоже, что с кодом, который вы опубликовали, что-то не так ...
Вы должны выполнить автоматический выпуск в первой функции, так как она не похожа на init, и вы вызываете init. Р>
В конце первой функции объект все еще действителен, так как вы добавили его в массив, который вызвал сохранение.
Между первой вызываемой функцией и второй вызываемой функцией кто-то освобождает объект, поэтому доступ к объекту приводит к сбою. Р>
Поместите точку останова в первую функцию, в освобождение объекта и вторую функцию, чтобы увидеть, кто освобождает ее перед вторым вызовом. Р>