Reading Code TWO

引入:读AFNetworking ~> '0.5.1'

一、NSAutoreleasePool

虽然ARC引入之后NSAutoReleasePool的使用有了很大变化,但是了解NSAutoReleasePool的机制还是十分必要的,下面主要说一下:

NSAutoReleasePool * pool = [NSAutoReleasePool alloc] init];
//do something
[[NSRunLoop currentRunLoop] run];
[pool drain];

之后,
[pool drain][pool release] 的区别:

  1. release,在引用计数环境下,由于NSAutoReleasePool是一个不可以被retain的类型,所以release会直接dealloc pool对象。当pool被dealloc的时候,pool向所有在pool中的对象发出一个release的消息,如果一个对象在这个pool中autorelease了多次,pool对这个对象的每一次autorelease都会release。在GC环境下release是一个no-op操作(代表没有操作,是一个占据进行很少的空间但是指出没有操作的计算机指令)。

  2. drain,在引用计数环境下,它的行为和release是一样的。在GC的环境下,这个方法调用objc_collect_if_needed出发GC。

因此,重点是:在GC环境下,release是一个no-op,所以除非你不希望在GC环境下出发GC,你都应该使用drain而不是使用release来释放pool。

引入:

- (void)setCancelled:(BOOL)isCancelled {
    [self willChangeValueForKey:@"isCancelled"];
    _cancelled = YES;
    [self didChangeValueForKey:@"isCancelled"];

    self.state = AFHTTPOperationFinishedState;
}
二、键-值编码(KVC)、KVO、NSNotificationCenter
键-值编码 KVC

setValue:forKey:通过名称(字符串)设置任何属性的值,字符串可在运行时修改

[aObject setValue:theValue forKey:theKey];

valueForKey:从对象中获取属性的值

NSString *aString = [aObject valueForKey:theKey];

其实与getter,setter一样,但更加灵活。

键-值观察 Key-Value Observing, KVO

控制器获知何时更新视图

  • 反复检查模型观察是否有任何更改
    1. 创建计时器,定期从模型中获取最新值,并提供给视图
    2. 浪费资源:时间,CPU,电池
  • 等待模型向控制器通知变化
  • 允许对象注册为 当另一个对象 更改它的一个属性的值时收到通知
  • 注册更改通知
  1. 当属性修改时,需要被通知的对象(观察者)
  2. 被观察者的属性名称
  3. 当一个变化发生时,观察者应该被告知的信息
  4. [optional]包含一个指针或引用,当属性值发生变化时,指针或对象引用应该被传递到运行的方法中
  • 注册(添加)通知
[aProduct addObserver:self
           forKeyPath:@"productName"
              options:(NSKeyValueObservingOptionNew|NSKeyValueObservingOptionOld)
              context:nil];
  • 当一个对象被注册为另一个对象的一个观察者时,该对象(如:观察者)将接收observeValueForKeyPath:ofObject:change:context:消息

  • 属性发生变化的对象

  • 发生变化的属性对象

  • 一个包含变化信息的NSDictionary

  • 当此消息被调用时,context变量将传递进去

 - (void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary *)change context:(void *)context
{
    if([keyPath isEqualToString:@"productName"])
    {
        NSString *newName = [change objectForKey:NSKeyValueChangeNew];
    
        //通知响相应视图根据newName变量的值进行更新
    }
}
  • NSDictionary包含不同的信息和其他键
  • NSKeyValueObservingOptionNew 属性要被设置的值
  • NSKeyValueObservingOptionOld 属性之前的值
  • 将变化通知给观察者

使用了Objective-C的属性@property,当setter被调用时,Cocoa自动通知任何已注册的观察者

不使用属性,或重写了setter,需要手动通知系统

对self对象调用willChangeValueForKey与didChangeValueForKey,跟踪新值,旧值
重写setter,同时允许KVO工作

- (void) setProductName:(NSString *)newProductName
{
    [self willchangeValueForKey:@"productName"];
    productName = newProductName;
    [self didChangeValueForKey:@"productName"];
}
使用NSNotification进行通知

某些相关联的事情发生,使用广播通知
按下Home键

  1. NSNotification对注册对象发送广播通知,由NSNotificationCenter管理,是单例对象
    相应Home键按下
  2. 注册通知
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(applicationEnteredBackground:) UIApplicationDidEnterBackgroundNotification object:nil];
  1. UIApplicationDidEnterBackgroundNotification传递出去,注册的对象将运行applicationenteredBackground:方法,此方法定义在该对象所属类中
- (void)applicationEnteredBackground:(NSNotification *)notification
{
    //进入后台,进行处理
}
  1. 不希望接收到消息
[[NSNotificationCenter defaultCenter] removeObserver:self]

引入:

在阅读AFN的源码的时候,发现只有(HTTP、Image)RequestOperation和AFRestClient。RequestOperation很好理解就是一项请求操作,里面包括了NSURLConnection的代理方法,在这里进行网络请求,得到服务器返回的数据,但是在这里并没有执行这个操作,只是把这个请求操作封装好了。(这个时候我就想应该会在某个地方调用[operation start]这个方法来获取数据,但是我搜索整个库,发现并没有地方调用这个操作,这就很纳闷了)AFN是怎么开始开始请求的呢,后面发现在AFRestClient里面用到了这个operation,AFRestClient先是对请求头,请求方法和请求参数进行了一次封装,然后就是执行相应的RequestOperation,但是这里也没有调用[operation start],只是调用了[self.operationQueue addOperation:operation]这时候去查资料,才有了下面的内容

AFHTTPRequestOperation *operation = [AFJSONRequestOperation operationWithRequest:request success:success failure:failure];
[self.operationQueue addOperation:operation];
三、Operation
  • 系统自动将NSOperationqueue中的NSOperation对象取出,将其封装的操作放到一条新的线程中执行。
    提示:队列的取出是有顺序的,与打印结果并不矛盾。这就好比,选手A,B,C虽然起跑的顺序是先A,后B,然后C,但是到达终点的顺序却不一定是A,B在前,C在后。
  • 只要NSBlockOperation封装的操作数 > 1,就会异步执行操作
  • NSOperationQueue的作⽤:NSOperation可以调⽤start⽅法来执⾏任务,但默认是同步执行的
  • 如果将NSOperation添加到NSOperationQueue(操作队列)中,系统会自动异步执行NSOperation中的操作
  • 添加操作到NSOperationQueue中,自动执行操作,自动开启线程
  • 操作对象默认在主线程中执行,只有添加到队列中才会开启新的线程。即默认情况下,如果操作没有放到队列中queue中,都是同步执行。只有将NSOperation放到一个NSOperationQueue中,才会异步执行操作。
  • 当我们把operation添加到队列中去后,就相当于把operation交给了系统,然后由系统决定它的执行顺序。
    从网上摘抄了一篇非常详细的Operation介绍
四、AFNetworking的内容
  • AFHTTPRequestOperation(NSOperation)

封装一整套请求操作,有NSURLConnection的代理方法,得到服务器返回的数据,还有对抽象类NSOperation的具体实现,是下面图片链接请求和JSON数据请求的基类

  • AFImageCache(NSCache)

对图片进行缓存和获取缓存图片,使用的是图片链接+图片的尺寸当做key缓存的

  • AFImageRequestOperation(AFHTTPRequestOperation)

单独对网络图片请求进行封装,对图片进行简单的处理,同时在请求到图片后,对图片进行缓存

  • AFJSONRequestOperation(AFHTTPRequestOperation)

处理返回结果,把结果JSON格式化,首先是判断没有错误,然后判断是否包含正确的状态码,如果不包含,自定义error,再判断是否包含正确MIMEType,如果不包含,自定义error,再判断如果错误,返回failure块,包含请求,响应,错误,如果返回结果长度为0,直接返回success,最后异步处理正常情况,请求成功,有数据,如果系统版本大于4.3,使用系统自带的NSJSONSerialization,对返回数据JSON化,如果小于4.3,使用第三方框架JSONKit,对返回数据JSON化,处理成功返回success(request, response, JSON),处理失败返回failure(request, response, JSONError)

  • AFNetworkActivityIndicatorManager(NSObject)

对状态栏网络信号小菊花的简单封装,开始和结束动画

  • AFRestClient(NSObject)

真正开始请求网络的地方,包含get、post、pull、delete请求方法,也可以取消网络请求,设置请求头

  • NSData + AFNetworking

NSData的扩展,包括base64编码,压缩和解压,使用的是zlib压缩函式库

  • NSMutableURLRequest + AFNetworking

NSMutableURLRequest的扩展,提供对请求体的处理方法

  • NSString + AFNetworking

NSString的扩展,提供对请求链接url使用当初ASI里面的方法编码CFURLCreateStringByAddingPercentEscapes

  • UIImage + AFNetworking

UIImage扩展,对UIImage进行裁剪,带圆角的裁剪

  • UIImageView + AFNetworking

UIImageView的扩展,提供给我们之间使用的,设置网络图片链接给UIImageView来展示图片,如果有缓存改图片,之间去缓存图片,取消网络请求

简单整理,如果错误,欢迎指正,谢谢~
持续更新

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 201,552评论 5 474
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 84,666评论 2 377
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 148,519评论 0 334
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,180评论 1 272
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,205评论 5 363
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,344评论 1 281
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 37,781评论 3 393
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,449评论 0 256
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,635评论 1 295
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,467评论 2 317
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,515评论 1 329
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,217评论 3 318
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,775评论 3 303
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,851评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,084评论 1 258
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 42,637评论 2 348
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,204评论 2 341

推荐阅读更多精彩内容

  • iOS Concurrency Programming Guide iOS 和 Mac OS 传统的并发编程模型是...
    YangPu阅读 831评论 0 2
  • 1.设计模式是什么? 你知道哪些设计模式,并简要叙述? 设计模式是一种编码经验,就是用比较成熟的逻辑去处理某一种类...
    司马DE晴空阅读 1,273评论 0 7
  • OC的理解与特性 OC作为一门面向对象的语言,自然具有面向对象的语言特性:封装、继承、多态。它既具有静态语言的特性...
    小楼昨夜有风雨阅读 563评论 0 0
  • 序言 目前形势,参加到iOS队伍的人是越来越多,甚至已经到供过于求了。今年,找过工作人可能会更深刻地体会到今年的就...
    Jack_lin阅读 78,293评论 110 1,945
  • 我剪一帖黄昏 裁一条静谧的小河 清清泠泠,有橘黄灯光的温柔 有星星点点的微风 装满温情的记忆 点缀初夏的风景 小河...
    如影悠然阅读 4,035评论 2 0