您的位置:首页 > 移动开发 > IOS开发

iOS多线程开发

2014-11-14 22:23 86 查看
先来理解一下线程和进程的区别和联系

区别:线程是CPU独立运行和独立调度的基本单位,可以理解为一个进程中执行的代码片段。

进程是资源分配的基本单位,进程中包含了某些资源的内存区域。

联系:进程是线程的容器,真正完成代码执行的是线程,而进程则作为线程的执行环境,一个程序中至少包含一个进程,一个进程至少包含一个线程,一个进程中的多个线程共享当前进程所拥有的全部资源。

多线程开发的优缺点:

优点:使用多线程开发可以把程序中占据时间长的任务放到后台去处理,如图片、视频的下载,还可以发挥多核处理器的优势,并发执行让系统运行的更好更流畅,用户体验更好

缺点:大量的线程降低代码的可读性,需要更多的内存空间,而且当多个线程对一个资源出现争夺的时候要注意线程安全的问题

线程的使用也不是无节制的,iOS中得主线程的堆栈大小是1M,从第二个线程开始都是512K,这些数值不能通过编译器开关或者API函数更改。

多线程开发时要注意更新UI界面时,处理界面和用户之间的交互事件一定要在主线程中处理

iOS创建多线程主要有三种方法:NSThread、NSOperatio和GCD(Grand Central Dispatch)

一、NSThread

轻量级,使用简单,每个NSThread对象对应一个线程,需要自己管理线程的生命周期、线程同步、加锁、睡眠以及唤醒等。线程同步对数据的加锁会有一定的系统开销 .

开启一个线程的3中方式:

//第一种,使用NSThread开启线程,手动开启

NSThread *thread = [[NSThread
alloc] initWithTarget:self
selector:@selector(selector1)
object:nil];

//开始执行

[thread start];

//第二种,NSThread自动开启

[NSThread detachNewThreadSelector:@selector(selector3) toTarget:self withObject:nil];

//第三种, 用的较多,在子线程中完成

//NSObject的方法, 开启一个线程执行耗时的操作

//开启后台线程执行任务的方法,方法本身是在主线程中执行的,而选择器指定的方法是在后台线程中进行的

[self
performSelectorInBackground:@selector(selector2)
withObject:nil];

//开启后台线程执行任务的方法,方法本身是在主线程中执行的,而选择器指定的方法是在后台线程中进行的

-(void)performSelectorInBackground:(SEL)aSelector withObject:(id)arg

{

}

//在后台中通知主线程执行任务的方法

-(void)performSelectorOnMainThread:(SEL)aSelector withObject:(id)arg waitUntilDone:(BOOL)wait

{

//得到当前的进程

//[NSThread currentThread];

//线程休眠

//[NSThread sleepForTimeInterval:1.0];

}

二、NSOperation

面向对象,不需要关心线程管理,数据同步的事情,可以把精力放在自己需要执行的操作上。NSOperation的是对线程的高度抽象,在项目中使用它, 会使项目的程序结构更好,子类化NSOperation的设计思路,是具有面向对象的优点,使得实现是多线程支持,而接口简单,可以在复杂项目中使用。

NSInvocationOperation * operation = [[NSInvocationOperationalloc] initWithTarget:self selector:@selector(printLargeNumber) object:nil];

NSInvocationOperation * operation2 = [[NSInvocationOperationalloc] initWithTarget:self selector:@selector(test) object:nil];

//创建一个操作队列, 队列FIFO, 先进先出

NSOperationQueue * queque = [[NSOperationQueue alloc] init];

//设置最大并发个数

[queque setMaxConcurrentOperationCount:2];

[queque addOperation:operation];

[queque addOperation:operation2];

三、GCD(共产党)

GCD是基于C语言的面向对象的苹果开发的一个多线程编程的解决方案。iOS4.0+才能使用,比NSThread,
NSOperation更为高效和强大,是苹果推荐使用的多线程技术。GCD本身非常简单易用,对于不复杂的多线程操作,会节省代码量,而Block参数的使用,会使代码更为易读,可以在简单项目中使用

//1.获得主队列:是一个单例,
运行在主线程, 给此队列中提交任务是串行执行的

dispatch_queue_t mainQueue =
dispatch_get_main_queue();

//2.全局队列,
第一个参数是优先级, 根据优先级的不同是4个单例,
第二个参数是预留参数

//全局队列是运行在子线程的,
任务是并发执行的

dispatch_queue_t globalQueue =
dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT,
0);

NSLog(@"globalQueue = %@", globalQueue);

dispatch_queue_t globalQueue2 =
dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_LOW,
0);

NSLog(@"globalQueue2 = %@", globalQueue2);

dispatch_queue_t globalQueue3 =
dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_BACKGROUND,
0);

NSLog(@"globalQueue3 = %@", globalQueue3);

dispatch_queue_t globalQueue4 =
dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_HIGH,
0);

NSLog(@"globalQueue4 = %@", globalQueue4);

//3.自定义队列
运行在子线程 创建的时候指定任务是串行还是并发

//DISPATCH_QUEUE_SERIAL
串行

// DISPATCH_QUEUE_CONCURRENT
并发

dispatch_queue_t customQueue =
dispatch_queue_create("com.lanou",
DISPATCH_QUEUE_CONCURRENT);

NSLog(@"customQueue = %@", customQueue);

//dispatch_async
异步执行队列, 不会等队列中的任务执行完,
就已经往下执行

dispatch_async(dispatch_get_main_queue(), ^{

for (int i =
0; i < 10000; i++) {

NSLog(@"i = %d", i);

}

});

//dispatch_sync
同步执行队列, 必须要等到队列中的任务执行完才会往下执行,
容易照成UI假死 dispatch_sync(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT,
0), ^{

for (int i =
0; i < 10000; i++) {

NSLog(@"i = %d", i);

}

});

//延迟调用,
延迟几秒执行

dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(3.0
* NSEC_PER_SEC)),
dispatch_get_main_queue(), ^{

NSLog(@"Test!");

});
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: