利用多线程进行优化
#import"ViewController.h"
#import"App.h"
@interfaceViewController()
@property(nonatomic,strong)NSArray*apps;
//内存缓存
@property(nonatomic,strong)NSMutableDictionary*imageDic;
@property(nonatomic,strong)NSOperationQueue*queue;
@property(nonatomic,strong)NSMutableDictionary*operation;
@end
@implementationViewController
- (NSMutableDictionary*)operation{
if(_operation==nil) {
_operation= [NSMutableDictionarydictionary];
}
return_operation;
}
- (NSOperationQueue*)queue{
if(_queue==nil) {
_queue= [[NSOperationQueuealloc]init];
//设置最大并发数
_queue.maxConcurrentOperationCount=5;
}
return_queue;
}
- (NSMutableDictionary*)imageDic{
if(_imageDic==nil) {
_imageDic= [NSMutableDictionarydictionary];
}
return_imageDic;
}
- (NSArray*)apps{
if(_apps==nil) {
NSArray*ary = [NSArrayarrayWithContentsOfFile:[[NSBundlemainBundle]pathForResource:@"apps"ofType:@"plist"]];
NSMutableArray*ary1 = [NSMutableArrayarray];
for(NSDictionary*dicinary) {
[ary1addObject:[AppappWithdic:dic]];
}
_apps= ary1;
}
return_apps;
}
- (NSInteger)tableView:(UITableView*)tableView numberOfRowsInSection:(NSInteger)section{
returnself.apps.count;
}
- (NSInteger)numberOfSectionsInTableView:(UITableView*)tableView{
return1;
}
- (UITableViewCell*)tableView:(UITableView*)tableView cellForRowAtIndexPath:(NSIndexPath*)indexPath{
staticNSString* ID =@"app";
UITableViewCell*cell =[tableViewdequeueReusableCellWithIdentifier:ID];
App*app =_apps[indexPath.row];
cell.textLabel.text= app.name;
cell.detailTextLabel.text=app.download;
//下载图片
//先查看图片在内存缓存中是否存在,如果存在,直接拿来用,但程序重新启动时,还要重新下载
//如果有磁盘缓存把磁盘缓存放到内存缓存,否则直接下载
//1.没有下载过
//2.下载过被销毁了
UIImage*imaged = [self.imageDicobjectForKey:app.icon];
if(imaged) {
cell.imageView.image=imaged;
NSLog(@"%ld---内存缓存",(long)indexPath.row);
}else{
NSString*Caches =NSSearchPathForDirectoriesInDomains(NSCachesDirectory,NSUserDomainMask,YES).lastObject;
NSString*filename = [app.iconlastPathComponent];
NSString* fullpath = [CachesstringByAppendingPathComponent:filename];
//检查磁盘缓存:
NSData*imageD = [NSDatadataWithContentsOfFile:fullpath];
if(imageD) {
UIImage*image = [UIImageimageWithData:imageD];
cell.imageView.image=image;
NSLog(@"%ld---磁盘缓存",(long)indexPath.row);
//把磁盘缓存放到内存缓存
[self.imageDicsetObject:imageforKey:app.icon];
}else{
//检查该操作是否在缓存中,如果是就什么也不做
NSBlockOperation*download = [self.operationobjectForKey:app.icon];
if(download) {
}else{
//先清空image,放个占位的图片
cell.imageView.image=[UIImageimageNamed:@"Snip20170530_1"];
download = [NSBlockOperationblockOperationWithBlock:^{
NSURL*url = [NSURLURLWithString:app.icon];
NSData*imageData = [NSDatadataWithContentsOfURL:url];
UIImage*image = [UIImageimageWithData:imageData];
//容错处理,防止url不正确,或者网络问题
if(image ==nil){
[self.operationremoveObjectForKey:app.icon];
return;
}
//演示网速慢的情况
[NSThreadsleepForTimeInterval:3.0];
NSLog(@"dowunload--%@",[NSThreadcurrentThread]);
//线程间通信
[[NSOperationQueuemainQueue]addOperationWithBlock:^{
//刷新某一行
[self.tableViewreloadRowsAtIndexPaths:@[indexPath]withRowAnimation:UITableViewRowAnimationLeft];
cell.imageView.image=image;
}];
//把图片保存在内存缓存里
[self.imageDicsetObject:imageforKey:app.icon];
[imageDatawriteToFile:fullpathatomically:YES];
NSLog(@"%ld",(long)indexPath.row);
//移除图片的下载缓存
[self.operationremoveObjectForKey:app.icon];
}];
//添加操作到操作缓存中
[self.operationsetObject:downloadforKey:app.icon];
//添加操作到队列
[self.queueaddOperation:download];
}
}
}
//打印沙盒路径
//NSLog(@"%@",NSSearchPathForDirectoriesInDomains(NSCachesDirectory, NSUserDomainMask, YES));
returncell;
}
//UI很不流畅-》开子线程下载
//图片重复下载-》缓存
//内存缓存-》磁盘缓存
//图片不会刷新:手动刷新,因为图片尺寸为0
//图片数据错乱
//图片重复下载:当图片还为完全下载之前,又要重新展示图片
//documents:手机连上itunes会备份,不允许把缓存数据放到这个路径。
//library:缓存路径:保存缓存数据偏好设置:保存一些账号信息
//tmp:临时路径,随时会被删除
@end
//如果出现内存警告
- (void)didReceiveMemoryWarning{
//不会影响图片显示
[self.imageDicremoveAllObjects];
//取消队列中所有操作
[self.queuecancelAllOperations];
}