窥探NSOperation

NSOperation是iOS开发中实现多线程的一种简便方式,它与GCD类似也是不需要开发者手动管理线程,只需要关注要实现的task即可。NSOperation属于CocoTouch框架,是面向对象的,它的底层是通过GCD实现的。

NSOperation相关知识点

NSOperation Queue

NSOperation与GCD类似,一般的使用方法都是把要实现的任务enqueue到相应的Queue中,Queue会管理相关的线程,然后任务就会执行。可以通过[NSOperationQueue mainQueue]或者标准的两段式[NSOperationQueue alloc] init]来创建。

串行队列or并行队列

可以通过maxConcurrentOperationCount设置队列属性,当maxConcurrentOperationCount= 1 是为串行队列,其它则为并行队列。

队列优先级

在iOS8以后可以设置队列的优先级,让重要的事情优先执行,队列的优先级是通过NSQualityOfService qualityOfService来设置,主要有4个级别,从高到低为:NSQualityOfServiceUserInteractive、NSQualityOfServiceUserInitiated、NSQualityOfServiceUtility和NSQualityOfServiceBackground。

NSOperation类

NSOperation是一个Abstract Class,它定义了基本的接口,不能直接使用,好在Foundation为我们提供了2个concrete subclass,分别为NSBlockOperation和NSInvocationOperation。类继承关系如下图所示:NSOperaion

NSOperation也定义了开始方法start和任务方法main,但一般都不会用到,平常真正使用的是NSBlockOperation和NSInvocationOperation。

NSBlockOperation&NSInvocationOperaion

NSBlockOperaion是通过Block的形势定义任务,例如创建NSBlockOperaion的API为:
+ (instancetype)blockOperationWithBlock:(void (^)(void))block;;
NSInvocationOperaion是标准的target-selector,创建的API为
- (nullable instancetype)initWithTarget:(id)target selector:(SEL)sel object:(nullable id)arg;

NSOperation状态管理

NSOperation可以通过cancelledexecutingfinishedready来查询当前的任务运行状态,上述状态都是通过KVO实现的。取消任务需调用cancel接口。

NSOperation优先级

NSOperaion可以通过NSOperationQueuePriority queuePriority来指定某个Operaion在Queue中执行的优先级。

任务依赖

当任务A依赖任务B时,用NSOperation实现时最方便的,伪代码如下:

//先执行B Operation,后执行A Operation
NSBlockOperation *A = [NSBlockOperation blockOperationWithBlock:^{
    NSLog(@"A Operation!!!!");
}];

NSBlockOperation *B = [NSBlockOperation blockOperationWithBlock:^{
    NSLog(@"B Operation!!!!");
}];
[A addDependency:B];

NSOperaion与GCD区别

  1. NSOperation是对象而GCD是C的API
  2. NSOperaion可以方便地查看某个任务的运行状态且可以任务取消Queue中的任务,但GCD却不行
  3. NSOperationQueue可以设置priority而Dispatch Queue不行
  4. NSOperation可以方便地设置任务之间的依赖关系,虽然GCD也可以通过dispatch_barrier_async()也能实现,但需要严格遵守添加次序,不够优雅简洁
  5. NSOperation可以方便地指定Operation的优先级,虽然GCD也可以通过dispatch_barrier_async()也能实现,但需要严格遵守添加次序,不够优雅简洁