我正在使用iphone games tutorial的第二部分,我对ccTouchesEnded
方法的实现感到困惑。这是实施“射击”的地方:玩家(大炮)转向触摸方向,弹丸射击。
我不清楚的部分是:_nextProjectile
似乎在它仍在使用时被释放(通过它下面的代码 - _nextProjectile runAction
)。
你能否解释为什么此时释放对象是安全的?
- (void)ccTouchesEnded:(NSSet *)touches withEvent:(UIEvent *)event {
[_player runAction:
[CCSequence actions:
[CCRotateTo actionWithDuration:rotateDuration angle:cocosAngle],
[CCCallBlock actionWithBlock:^{
// OK to add now - rotation is finished!
[self addChild:_nextProjectile];
[_projectiles addObject:_nextProjectile];
// Release
[_nextProjectile release];
_nextProjectile = nil;
}],
nil]];
// Move projectile to actual endpoint
[_nextProjectile runAction:
[CCSequence actions:
[CCMoveTo actionWithDuration:realMoveDuration position:realDest],
[CCCallBlockN actionWithBlock:^(CCNode *node) {
[_projectiles removeObject:node];
[node removeFromParentAndCleanup:YES];
}],
nil]];
}
答案 0 :(得分:1)
早些时候在 ccTouchesEnded:withEvent:中,您增加了此行 _nextProjectile 的保留计数:
_nextProjectile = [[CCSprite spriteWithFile:@"projectile2.png"] retain];
因此,稍后您必须减少保留计数以防止内存泄漏。换句话说:您有责任释放此保留。这就是这条线的来源:
[_nextProjectile release];
为什么在那时释放它是安全的?您在问题中发布的代码片段实际上都是一系列操作中的操作。
[_player runAction:[CCSequence actions:...]];
对对象执行操作会增加该对象的保留计数。这意味着操作对象本身会创建并保存对 _nextProjectile 的另一个引用。操作序列是在实际执行操作之前创建的,因此操作对象已经具有对 _nextProjectile 的引用。因此,在其中一个动作中释放它实际上是安全的。他们等待释放 _nextProjectile ,直到这些行通过:
[self addChild:_nextProjectile];
[_projectiles addObject:_nextProjectile];
这些行之前的版本可能(我没有查看除 ccTouchesEnded:withEvent:之外的任何其他代码)导致EXC_BAD_ACCESS运行时错误。
以下是有关保留计数的更多信息:cocos2d forum