我正在使用标准缓存方法来缓存从Documents目录加载的一些UIImages。图像显示在UITableView中。它们非常大 - 图像本身高达600x600,并且在240x180的图像视图中显示(在视网膜显示器上,因此差异不大)。
当新细胞即将上线时,实时加载图像会导致一些延迟。所以我在处理图像的对象中实现了一个缓存方法:
- (UIImage *)imageWithStyle:(NSString *)styleName {
NSLog(@"looking for image %@", self.imageFileName);
/* if we have a cached image in dictionary, return it */
if (imageCache == nil) imageCache = [[NSMutableDictionary alloc] init];
UIImage *returnImage = [imageCache objectForKey:styleName];
if (returnImage != nil) {
NSLog(@"returning cached image");
return returnImage;
}
/* otherwise, look for image at path */
NSString *path = [self cacheFilePathWithStyle:styleName];
UIImage * originalImage = [[UIImage alloc] initWithContentsOfFile:path];
/* if image doesnt exist at path, start download and return nil */
if (originalImage == nil) {
NSLog(@"image not found. downloading.");
[self downloadImageFromS3];
return nil;
}
/* found image at path */
/* scale image for screen */
if ([[UIScreen mainScreen] respondsToSelector:@selector(scale)] && [[UIScreen mainScreen] scale] == 2){
returnImage = [UIImage imageWithCGImage:[[originalImage autorelease] CGImage] scale:2.0 orientation:UIImageOrientationUp];
NSLog(@"scaling image for retina");
} else {
returnImage = [originalImage autorelease];
NSLog(@"image scaled for standard resolution");
}
/* cache image in dictionary */
NSLog(@"caching image");
[imageCache setObject:returnImage forKey:styleName];
return returnImage;
}
在屏幕上出现tableview之前,我强制所有图像处理对象运行此缓存方法,以确保图像存在于字典中,以便在需要显示时检索。通过NSLog,我可以看到事情正在发挥作用。
我现在正在获得无滞后性能,但只有在图像出现在屏幕上之后才会出现。所以,当我最初看到tableview时,我向下滚动并且NSLogs告诉我正在从缓存中检索图像,但我仍然得到相同的加载延迟。在一个单元格出现在屏幕上一次之后,它会加载而没有延迟。
这里有什么我想念的吗?还有什么我必须要实际缓存图像吗?加载它并将其放入字典似乎没有办法。
谢谢!
更新
我现在已经放弃了。有一些尝试通过在新的上下文中绘制来强制图像加载,但此时我不熟悉核心图形编程。我已经尝试了一些人们共享的代码,但没有运气。
相反,我会在tableview滚动时显示图像的低分辨率版本,并在tableview停止滚动时加载高分辨率版本,如通过其委托方法所宣布的那样。至少我知道这种方法适用于任意数量的图像。
答案 0 :(得分:0)
来自-[UIImage initWithContentsOfFile:]
的文档:
此方法将图像数据加载到内存中并将其标记为可清除。如果数据被清除并需要重新加载,则图像对象将从指定路径再次加载该数据。
我的猜测是,通过将所有图像加载到内存中,您的应用程序会消耗太多内存,导致UIImage
类释放它稍后可以从文件重新加载的图像数据。
答案 1 :(得分:0)
如果您使用[UIImage imageNamed:]
,它将为您完成所有这些缓存业务。无需滚动自己的缓存,然后想知道它是否正常工作。
使用该方法的好处和缺点。好处:如果你使用相同的图像文件两次,它实际上不会加载两次,从而节省了你的内存。缺点:缓存会对记忆产生很大的影响,无论你是否自己动手,你都会想到这么做。