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

ios中的多线程

2016-03-08 00:57 295 查看
主线程:线程是进程的基本执行单元,一个iOS程序运行后,默认会开启1条线程,称为“主线程”又叫“UI线程”

主线程的主要作用

1.显示\刷新UI界面

2.处理UI事件(比如点击事件、滚动事件、拖拽事件等)

iOS有四个多线程解决方案

一. Pthreads

这是一套在很多操作系统上都通用的多线程API,所以移植性很强(然并卵),当然在 iOS 中也是可以的。不过这是基于 c语言

的框架,使用起来这酸爽!感受一下

1.包含头文件

#import <pthread.h>


2.创建线程,并执行任务

- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event {
pthread_t thread;
//创建一个线程并自动执行
pthread_create(&thread, NULL, start, NULL);
}

void *start(void *data) {
NSLog(@"%@", [NSThread currentThread]);

return NULL;
}


到了这里也许你还会问 到底这个线程到底操作了什么 别急 跟着小龙哥看下一个

二.NSThread

经过苹果封装后的,并且完全面向对象的。所以你可以直接操控线程对象,非常直观和方便。但是,它的生命周期还是需要我们手动管理,所以这套方案也是偶尔用用,比如 [NSThread currentThread],它可以获取当前线程类,你就可以知道当前线程的各种属性,用于调试十分方便。下面来看看它的一些用法。

1.创建启动异步

// 创建
NSThread *thread = [[NSThread alloc] initWithTarget:self selector:@selector(run:) object:nil];

// 启动
[thread start];


2.创建启动同步完成

1.直接创建并自动启动
[NSThread detachNewThreadSelector:@selector(run:) toTarget:self withObject:nil];


2.使用 NSObject 的方法创建并自动启动
[self performSelectorInBackground:@selector(run:) withObject:nil];


注意:

Note: The performSelector: method and related selector-invoking methods are not imported in Swift because they are inherently unsafe.

因为安全问题 苹果在swift中取消了performSelector这个方法

3.NSThread常用方法

除了创建启动外,NSThread 还以很多方法,下面我列举一些常见的方法,当然我列举的并不完整,更多方法大家可以去类的定义里去看。

//取消线程
- (void)cancel;

//启动线程
- (void)start;

//判断某个线程的状态的属性
@property (readonly, getter=isExecuting) BOOL executing;
@property (readonly, getter=isFinished) BOOL finished;
@property (readonly, getter=isCancelled) BOOL cancelled;

//设置和获取线程名字
-(void)setName:(NSString *)n;
-(NSString *)name;

//获取当前线程信息
+ (NSThread *)currentThread;

//获取主线程信息
+ (NSThread *)mainThread;

//使当前线程暂停一段时间,或者暂停到某个时刻
+ (void)sleepForTimeInterval:(NSTimeInterval)time;
+ (void)sleepUntilDate:(NSDate *)date;


三.GCD

Grand Central Dispatch 主要的线程优化技术

他最伟大的优点在于它会自动管理线程的生命周期(创建线程、调度任务、销毁线程)使用起来非常方便

1.如何使用GCD

首先我们要明白两个非常重要的概念

任务:即操作,你想要干什么,说白了就是一段代码,在 GCD 中就是一个 Block,所以添加任务十分方便。任务有两种执行方式: 同步执行 和 异步执行,他们之间的区别是 是否会创建新的线程。

同步(sync) 和 异步(async) 的主要区别在于会不会阻塞当前线程,直到 Block 中的任务执行完毕!

如果是 同步(sync) 操作,它会阻塞当前线程并等待 Block 中的任务执行完毕,然后当前线程才会继续往下运行。

如果是 异步(async)操作,当前线程会直接往下执行,它不会阻塞当前线程。

队列:用于存放任务。一共有两种队列, 串行队列 和 并行队列

2.创建队列

1.主队列

dispatch_queue_t queue = ispatch_get_main_queue();


自己创建的队列:

自己可以创建 串行队列, 也可以创建 并行队列。第二个参数用来表示创建的队列是串行的还是并行的

2.1创建串行队列

DISPATCH_QUEUE_SERIAL 或 NULL 表示

2.2创建并行队列

-DISPATCH_QUEUE_CONCURRENT

//串行队列
dispatch_queue_t queue = dispatch_queue_create("tk.bourne.testQueue", NULL);
dispatch_queue_t queue = dispatch_queue_create("tk.bourne.testQueue", DISPATCH_QUEUE_SERIAL);
//并行队列
dispatch_queue_t queue = dispatch_queue_create("tk.bourne.testQueue", DISPATCH_QUEUE_CONCURRENT);


3.全局并行队列

只要是并行任务一般都加入到这个队列。这是系统提供的一个并发队列。

dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);


3.创建任务

同步任务:会阻塞当前线程 (SYNC)

dispatch_sync(<#queue#>, ^{
//code here
NSLog(@"%@", [NSThread currentThread]);
});


异步任务:不会阻塞当前线程 (ASYNC)

dispatch_async(<#queue#>, ^{
//code here
NSLog(@"%@", [NSThread currentThread]);
});


4.队列组

队列组可以将很多队列添加到一个组里,这样做的好处是,当这个组里所有的任务都执行完了,队列组会通过一个方法通知我们。下面是使用方法,这是一个很实用的功能。

//1.创建队列组
dispatch_group_t group = dispatch_group_create();
//2.创建队列
dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);

//3.多次使用队列组的方法执行任务, 只有异步方法
//3.1.执行3次循环
dispatch_group_async(group, queue, ^{
for (NSInteger i = 0; i < 3; i++) {
NSLog(@"group-01 - %@", [NSThread currentThread]);
}
});

//3.2.主队列执行8次循环
dispatch_group_async(group, dispatch_get_main_queue(), ^{
for (NSInteger i = 0; i < 8; i++) {
NSLog(@"group-02 - %@", [NSThread currentThread]);
}
});

//3.3.执行5次循环
dispatch_group_async(group, queue, ^{
for (NSInteger i = 0; i < 5; i++) {
NSLog(@"group-03 - %@", [NSThread currentThread]);
}
});

//4.都完成后会自动通知
dispatch_group_notify(group, dispatch_get_main_queue(), ^{
NSLog(@"完成 - %@", [NSThread currentThread]);
});


四 NSOperation & NSOperationQueue

NSOperation 是苹果公司对 GCD 的封装,完全面向对象,所以使用起来更好理解。 大家可以看到 NSOperation 和

NSOperationQueue 分别对应 GCD 的 任务 和 队列 。操作步骤也很好理解

五 NSOperation & NSOperationQueue

我们进行完多线程操作或 都需要回到主线程 接下来 就是讲到上面的四种方法是如何回到主线程(UI线程逻辑中的)

5.1 NSThread

[self performSelectorOnMainThread:@selector(run) withObject:nil waitUntilDone:NO];


5.2 GCD

dispatch_async(dispatch_get_main_queue(), ^{

});


5.3 NSOperationQueue

[[NSOperationQueue mainQueue] addOperationWithBlock:^{

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