iPhone UIImage - 如果两次遇到同一张图像,图像随机化器会崩溃
我正在构建一个随机提取图像的游戏。经过一些测试后,我意识到如果同一个图像被调用两次,它就会崩溃。我在完成第一款游戏后了解到这一点,我返回游戏主菜单并选择再次玩。我最终得到了一张在我之前的游戏中已经显示给我的图像,一秒钟后我的应用程序崩溃了。我做了一些测试,并在我的第一场游戏中使同一个图像显示了两次,并且在第二次显示图像后它崩溃了。
这是示例代码。 “idNum”和“timer”在 .h 文件中声明,因此它们是全局的。正如你所看到的,我有 NSTimer 每秒运行一次以随机化要拉取的新图像。直到图像尝试第二次显示为止一直有效。假设我得到一个随机顺序 1,3,2,5,3。第二个就崩溃了 3.
不能调用一个图像两次吗?我只能认为这是一个缓存问题,我不知道如何释放图像缓存。我收到错误 objc_msgSend。抱歉,不太擅长调试崩溃。
//idNum = the randomly generated integer
//pictures are called by numbers ex(1.jpg, 5.jpg)
timer = [NSTimer scheduledTimerWithTimeInterval:1 target:self selector:@selector(timeCounter) userInfo:nil repeats:YES];
-(void)timeCounter {
time = time + 1;
idNum = (arc4random() % 5);
NSString * imgIDnum = [[NSString alloc] initWithFormat:@"%d", idNum];
imgMain = [NSString stringWithFormat:@"%@%@", imgIDnum, @".jpg"];
[imgIDnum release];
UIImage * daImg = [UIImage imageNamed:imgMain];
[imgView setImage:daImg];
}
I am building a game that pulls images randomly. After doing some testing I have realized if the same image is called twice, it crashes. I learned this by after completing the first game, I returned to the games main menu and selected to play again. I ended up getting an image which was already displayed to me in my previous game and a second later my app crashed. I did some testing and made the same image show up twice during my first game, and it crashed a second after the image was displayed a second time.
Here is a sample code. "idNum" and "timer" are declared in the .h file so they are global. As you can see I have NSTimer that runs every second to randomize a new image to be pulled. Works find until an image is trying to be shown for a second time. Say I get a random order of 1,3,2,5,3. It will crash on the second 3.
Can you not call an image twice? I can only think that this is a caching issue, I am not sure how to release the image cache. I get the error objc_msgSend. Sorry not very good at debugging crashes.
//idNum = the randomly generated integer
//pictures are called by numbers ex(1.jpg, 5.jpg)
timer = [NSTimer scheduledTimerWithTimeInterval:1 target:self selector:@selector(timeCounter) userInfo:nil repeats:YES];
-(void)timeCounter {
time = time + 1;
idNum = (arc4random() % 5);
NSString * imgIDnum = [[NSString alloc] initWithFormat:@"%d", idNum];
imgMain = [NSString stringWithFormat:@"%@%@", imgIDnum, @".jpg"];
[imgIDnum release];
UIImage * daImg = [UIImage imageNamed:imgMain];
[imgView setImage:daImg];
}
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
您应该提供有关崩溃的更多信息。是在上面的 +imageNamed: 行中,还是在
-setImage:
中?最可能的原因是您过度释放了
UIImage
。例如,如果您在上述代码之后调用[daImg release]
,那么您将得到此行为,因为您将过度释放UIImage
类所包含的内容缓存。在出现您描述的情况之前,这不会导致崩溃。我见过这个 bug 的一个非常有趣的版本:我的一个队友过度释放了一个 NSNumber(大多数时候它恰好是整数 2)。 NSNumbers 是在内部缓存的,所以下次他在程序的不相关部分为整数 2 创建 NSNumber 时,程序就会崩溃。任何其他数字都可以,但尝试
NSLog()
2,然后繁荣。You should provide more information about the crash. Is it in the
+imageNamed:
line above, or perhaps in-setImage:
?The most likely cause is that you are over-releasing the
UIImage
. For instance, if you're calling[daImg release]
after the above code, then you would get this behavior because you would be over-releasing something that theUIImage
class is caching. This wouldn't cause a crash until the situation you describe.I've seen a really entertaining version of this bug: a teammate of mine was over-releasing an NSNumber (it happened to be for the integer 2 most of the time). NSNumbers are cached internally, so the next time he created an NSNumber for the integer 2, in an unrelated part of the program, it would crash. Any other number was fine, but try to
NSLog()
a 2, and boom.好吧,我很遗憾地说我已经解决了这个问题,但不知道如何解决。我最终重写了大部分代码,添加、删除和更改了一些代码片段,以便对内存管理更加友好。当我再次运行它时,一切都很好。抱歉没有解决办法。如果其他人遇到这个问题,请告诉我,我会尽力提供帮助。
Well I am sorry to say that I have fixed the issue and have no idea how. I ended up re-writing majority of that code, adding, removing and changing some snippets around to be more memory management friendly. When I went to run it again things were perfectly fine. Sorry for no solution. If someone else comes across this problem, let me know I will try and help.