iOS开发多线程篇—多线程简单介绍
2016-01-04 12:13
441 查看
基本概念
同步:在当前线程中执行任务,不具备开启新线程的能力异步:在新的线程中执行任务,具备开启新线程的能力
串行:一个任务执行完毕后,再执行下一个任务
并行:多个任务同时执行
并发:多个事件在同一个时间间隔内发生,但任一时刻只有一个程序运行
线程同步:多条线程安顺序执行
阻塞(blocking):表示需要等待A事件完成后才能完成B事件,称作A会阻塞B,通俗来讲就是强制等待的意思
死锁(deadlock):表示由于某些互相阻塞,也就是互相的强制等待,形成了闭环,导致大家永远互相阻塞下去了,Always and Forever,也就是死锁。
一、进程和线程
1.什么是进程
进程是指在系统中正在运行的一个应用程序,每个进程之间是独立的,每个进程均运行在其专用且受保护的内存空间内。比如:
打开QQ、Xcode,系统就会分别启动2个进程
2.什么是线程
线程是进程的基本执行单元,一个进程(程序)的所有任务都在线程中执行,1个进程要想执行任务,必须得有线程(每1个进程至少要有1条线程)。比如:
使用酷狗播放音乐、使用迅雷下载电影,都需要在线程中执行.
3.线程是串行
1个线程中任务的执行是串行的,如果要在1个线程中执行多个任务,那么只能一个一个地按顺序执行这些任务。也就是说,在同一时间内,1个线程只能执行1个任务比如:
在1个线程中下载3个文件(分别是文件A、文件B、文件C)
二、多线程
1.什么是多线程
1个进程中可以开启多条线程,每条线程可以并行(同时)执行不同的任务,多线程技术可以提高程序的执行效率。比如:
同时开启3条线程分别下载3个文件(分别是文件A、文件B、文件C)
2.多线程的原理
同一时间,CPU只能处理1条线程,只有1条线程在工作(执行),多线程并发(同时)执行,其实是CPU快速地在多条线程之间调度(切换),如果CPU调度线程的时间足够快,就造成了多线程并发执行的假象。思考:如果线程非常非常多,会发生什么情况?
CPU会在N多线程之间调度,CPU会累死,消耗大量的CPU资源,每条线程被调度执行的频次会降低(线程的执行效率降低)。
3.多线程的优缺点
多线程的优点:能适当提高程序的执行效率
能适当提高资源利用率(CPU、内存利用率)
多线程的缺点:
开启线程需要占用一定的内存空间(默认情况下,主线程占用1M,子线程占用512KB)。如果开启大量的线程,会占用大量的内存空间,降低程序的性能,线程越多,CPU在调度线程上的开销就越大,程序设计更加复杂:比如线程之间的通信、多线程的数据共享
4.多线程在iOS开发中的应用
主线程:一个iOS程序运行后,默认会开启1条线程,称为“主线程”或“UI线程”。
主线程的主要作用:
1.显示\刷新UI界面 2.处理UI事件(比如点击事件、滚动事件、拖拽事件等)
注意:
别将比较耗时的操作放到主线程中。耗时操作会卡住主线程,严重影响UI的流畅度,给用户一种“卡”的坏体验。
iOS开发多线程篇—线程安全
一、多线程的安全隐患
资源共享,1块资源可能会被多个线程共享,也就是多个线程可能会访问同一块资源。比如:
多个线程访问同一个对象、同一个变量、同一个文件。当多个线程访问同一块资源时,很容易引发数据错乱和数据安全问题
二、安全隐患分析
[b]1 产生问题:[/b][b]2 解决问题:[/b]
三、如何解决
1.使用互斥锁互斥锁的使用前提:
多条线程抢夺同一块资源 。 互斥锁,就是使用了线程同步技术。 线程同步既是多条线程按顺序地执行任务。
@synchronized(锁对象) { // 需要锁定的代码 } 例如: //只能一把锁 @synchronized(self) { NSLog(@"示例代码"); }
注意:锁定1份代码只用1把锁,用多把锁是无效的
2 互斥锁的优缺点
优点:能有效防止因多线程抢夺资源造成的数据安全问题
缺点:需要消耗大量的CPU资源
3 死锁产生的四个条件
互斥条件:一个资源每次只能被一个进程使用
请求和保持请求:一个进程因请求资源而阻塞时,对已获得的资源保持不放
不剥夺条件:进程已获得的资源,在未使用完之前,不能强行剥夺
循环等待条件:若干进程之间形成一种头尾相接的循环等待的资源关系
四:原子和非原子属性
OC在定义属性时有nonatomic和atomic两种选择atomic:原子属性,为setter方法加锁(默认就是atomic)。线程安全,需要消耗大量的资源
nonatomic:非原子属性,不会为setter方法加锁。非线程安全,适合内存小的移动设备。
//atomic加锁原理 @property (assign, atomic) int age; - (void)setAge:(int)age { @synchronized(self) { _age = age; } }
五 iOS开发的建议
所有属性都声明为nonatomic尽量避免多线程抢夺同一块资源
尽量将加锁、资源抢夺的业务逻辑交给服务器端处理,减小移动客户端的压力
iOS开发多线程篇—线程间通信
1 创建线程
(1)手动创建线程,可以进行详细设置NSThread *thread = [[NSThread alloc] initWithTarget:self selector:@selector(run:) object:@"可以是run的参数,也可以为nil"]; [thread setName:@"线程名字"]; //线程的调度优先级:调度优先级的取值范围是0.0 ~ 1.0,默认0.5,值越大,优先级越高 [thread setThreadPriority:0.5]; //是否是主线程 [thread isMainThread]; //手动开始 [thread start]; //获得主线程 NSThread *mainThread = [NSThread mainThread]; //获取当前线程 NSThread *currentThread = [NSThread currentThread]; [self performSelectorInBackground:@selector(run:) withObject:@"1"];
(2)创建线程后自动启动线程
[NSThread detachNewThreadSelector:@selector(run) toTarget:self withObject:nil];
(3)隐式创建并启动线程
[self performSelectorInBackground:@selector(run) withObject:nil];
上述2种创建线程方式的优缺点
优点:简单快捷
缺点:无法对线程进行更详细的设置
2 线程通信
1 一个线程传递数据给另一个线程 2 在一个线程中执行完特定任务后,转到另一个线程继续执行任务
2.1
NSObject中的一些方法:
在应用程序主线程中做事情:
performSelectorOnMainThread:withObject:waitUntilDone:
performSelectorOnMainThread:withObject:waitUntilDone:modes:
在指定线程中做事情:
performSelector:onThread:withObject:waitUntilDone:
performSelector:onThread:withObject:waitUntilDone:modes:
waitUntilDone参数是个bool值,如果设置为NO,相当于异步执行,当前函数执行完,立即执行后面的语句。如果设置为YES,相当于同步执行,当前线程要等待Selector中的函数执行完后再执行。
在当前线程中做事情:
performSelector:withObject:afterDelay:
performSelector:withObject:afterDelay:inModes:
取消发送给当前线程的某个消息
cancelPreviousPerformRequestsWithTarget:
cancelPreviousPerformRequestsWithTarget:selector:object:
2 .2
GCD一个线程传递数据给另一个线程
dispatch_queue_t concurrentQueue2 = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0); dispatch_async(concurrentQueue2, ^{ __block UIImage *image2 = nil; NSLog(@"2"); NSLog(@"%@",[NSThread currentThread]); dispatch_sync(concurrentQueue2, ^{ /* Download the image here */ NSLog(@"3"); NSLog(@"%@",[NSThread currentThread]); }); dispatch_sync(dispatch_get_main_queue(), ^{ /* Show the image to the user here on the main queue*/ NSLog(@"4"); NSLog(@"%@",[NSThread currentThread]); }); });
iOS进程间通信之CFMessagePort
原文:
1.iOS开发多线程篇—多线程简单介绍
相关文章推荐
- iOS开发-装饰模式
- <填坑手册>Vuforia上架ios,以及分享功能注意事项
- iOS开发 关于ALAsset获取图库图片分辨率iOS7/iOS9适配
- iOS开发- 相机(摄像头)获取到的图片自动旋转90度解决办法
- iOS 精度问题
- iOS库.a与.framework
- iOS沙盒路径总结及存储方法
- iOS国际化
- nagios 监控
- IOSc程序中按钮点击不灵敏 ios
- iOS 头像圆角问题
- Bios工程师手边事—SATA
- 为什么用phonegap开发iOS应用
- 深入NSTimer(iOS)
- iOS-----推送机制(下)
- 不让苹果开发者账号折磨我
- iOS NSLocale相关方法
- 不让苹果开发者账号折磨我
- iOS文章收集
- iOS获取对象属性列表