iOS多线程编程之NSOperation和NSOperationQueue的使用

本文介绍了NSOperation的两种使用方式:NSInvocationOperation和NSBlockOperation,以及通过继承NSOperation来自定义操作。文章还详细讲解了如何控制线程池中的线程数量,并对比了NSOperationQueue与GCD的优点。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

著作权声明:本文由http://blog.youkuaiyun.com/totogo2010/原创

使用 NSOperation的方式有两种,

一种是用定义好的两个子类:

NSInvocationOperation 和 NSBlockOperation。

另一种是继承NSOperation

如果你也熟悉Java,NSOperation就和java.lang.Runnable接口很相似。和Java的Runnable一样,NSOperation也是设计用来扩展的,只需继承重写NSOperation的一个方法main。相当与java 中Runnalbe的Run方法。然后把NSOperation子类的对象放入NSOperationQueue队列中,该队列就会启动并开始处理它。


NSInvocationOperation例子:

和前面一篇博文一样,我们实现一个下载图片的例子。新建一个Single View app,拖放一个ImageView控件到xib界面。

实现代码如下:

#import "ViewController.h"
#define kURL @"http://avatar.youkuaiyun.com/2/C/D/1_totogo2010.jpg"

@interface ViewController ()

@end

@implementation ViewController

- (void)viewDidLoad
{
    [super viewDidLoad];
    NSInvocationOperation *operation = [[NSInvocationOperation alloc]initWithTarget:self
                                                                           selector:@selector(downloadImage:)
                                                                             object:kURL];
    
    NSOperationQueue *queue = [[NSOperationQueue alloc]init];
    [queue addOperation:operation];
	// Do any additional setup after loading the view, typically from a nib.
}

-(void)downloadImage:(NSString *)url{
    NSLog(@"url:%@", url);
    NSURL *nsUrl = [NSURL URLWithString:url];
    NSData *data = [[NSData alloc]initWithContentsOfURL:nsUrl];
    UIImage * image = [[UIImage alloc]initWithData:data];
    [self performSelectorOnMainThread:@selector(updateUI:) withObject:image waitUntilDone:YES];
}
-(void)updateUI:(UIImage*) image{
    self.imageView.image = image;
}

  1. viewDidLoad方法里可以看到我们用NSInvocationOperation建了一个后台线程,并且放到NSOperationQueue中。后台线程执行downloadImage方法。
  2. downloadImage 方法处理下载图片的逻辑。下载完成后用performSelectorOnMainThread执行主线程updateUI方法。
  3. updateUI 并把下载的图片显示到图片控件中。

第二种方式继承NSOperation 

在.m文件中实现main方法,main方法编写要执行的代码即可。

如何控制线程池中的线程数?

队列里可以加入很多个NSOperation, 可以把NSOperationQueue看作一个线程池,可往线程池中添加操作(NSOperation)到队列中。线程池中的线程可看作消费者,从队列中取走操作,并执行它。

通过下面的代码设置:
[queue setMaxConcurrentOperationCount:5];
线程池中的线程数,也就是并发操作数。默认情况下是-1,-1表示没有限制,这样会同时运行队列中的全部的操作。

@interface YourOperation : NSOperation
@end

@implementation YourOperation
- (void)main{
     // 任务代码
     ...
}
@end

@implementation YourOperation
- (void)start
{
    self.isExecuting = YES;
    // 任务代码 ...
}
- (void)finish //异步回调
{
    self.isExecuting = NO;
    self.isFinished = YES;
}
@end

1. 使用 main方法非常简单,开发者不需要管理一些状态属性(例如 isExecuting 和 isFinished),当 main 方法返回的时候,这个 operation 就结束了。这种方式使用起来非常简单,但是灵活性相对重写 start 来说要少一些, 因为main方法执行完就认为operation结束了,所以一般可以用来执行同步任务。

2. 如果你希望拥有更多的控制权,或者想在一个操作中可以执行异步任务,那么就重写 start方法, 但是注意:这种情况下,你必须手动管理操作的状态, 只有当发送 isFinished的 KVO 消息时,才认为是 operation 结束。

当实现了start方法时,默认会执行start方法,而不执行main方法。为了让操作队列能够捕获到操作的改变,需要将状态的属性以配合 KVO的方式进行实现。如果你不使用它们默认的 setter 来进行设置的话你就需要在合适的时候发送合适的 KVO消息。

需要手动管理的状态有:

    isExecuting
    代表任务正在执行中
    isFinished
    代表任务已经执行完成
    isCancelled
    代表任务已经取消执行
    手动的发送 KVO消息, 通知状态更改如下 :

[self willChangeValueForKey:@"isCancelled"];
_isCancelled = YES;
[self didChangeValueForKey:@"isCancelled"];

为了能使用操作队列所提供的取消功能,你需要在长时间操作中时不时地检查 isCancelled属性, 比如在一个长的循环中:

@implementation MyOperation

- (void)main
{
    while (notDone && !self.isCancelled) {
        // 任务处理
    }
}
@end

NSOperationQueue相对于GCD来说有以下优点:

  • 提供了在 GCD 中不那么容易复制的有用特性。
  • 可以很方便的取消一个NSOperation的执行
  • 可以更容易的添加任务的依赖关系
  • 提供了任务的状态:isExecuteing, isFinished.
内容概要:本文系统介绍了基于C#(VS2022+.NET Core)与HALCON 24.11的工业视觉测量拟合技术,涵盖边缘提取、几何拟合、精度优化及工业部署全流程。文中详细解析了亚像素边缘提取、Tukey抗噪算法、SVD平面拟合等核心技术,并提供了汽车零件孔径测量、PCB焊点共面性检测等典型应用场景的完整代码示例。通过GPU加速、EtherCAT同步等优化策略,实现了±0.01mm级测量精度,满足ISO 1101标准。此外,文章还探讨了深度学习、量子启发式算法等前沿技术的应用前景。 适合人群:具备一定编程基础,尤其是熟悉C#HALCON的工程师或研究人员,以及从事工业视觉测量与自动化检测领域的技术人员。 使用场景及目标:①学习如何使用C#HALCON实现高精度工业视觉测量系统的开发;②掌握边缘提取、抗差拟合、3D点云处理等核心技术的具体实现方法;③了解工业部署中的关键技术,如GPU加速、EtherCAT同步控制、实时数据看板等;④探索基于深度学习量子计算的前沿技术在工业视觉中的应用。 其他说明:本文不仅提供了详细的理论分析技术实现,还附有完整的代码示例实验数据,帮助读者更好地理解实践。同时,文中提到的硬件选型、校准方法、精度验证等内容,为实际项目实施提供了重要参考。文章最后还给出了未来的技术演进方向开发者行动建议,如量子-经典混合计算、自监督学习等,以及参与HALCON官方认证开源社区的建议。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值