点击查看我的回答
进程是系统的最小单元,一个程序在系统中拥有一个进程。系统由多个进程组成,一个进程拥有独立的内存区域。一个进程可以拥有多个线程,但是一定存在一个主线程。线程之间公用内存区域。主线程最大拥有1M的内存空间,子线程最大拥有512K的内存空间。点击查看回答
因为CPU一次只能执行一个任务,但是CPU的处理速度十分的快。迅速的切换处理任务,就造成了并发执行的假象。这样的处理任务就叫做多线程。 多线程是从硬件或者软件实现多个线程并发执行的技术。查看回答
优点是可以充分的利用多核的特性充分的利用资源,可以节省等待任务完成的时间。缺点是新增加一个子线程就要开辟512K的内存空间,造成内存暴涨。CPU的调用任务增多,造成运行温度升高,如果创建的子线程过多,可能造成程序卡死。多线程因为是资源共享,如果加锁不当则直接导致崩溃,加锁会影响程序的运行性能。查看答案
创建一个线程需要消耗90毫秒在栈创建512K的内存空间,占据1K的内核空间。查看答案
-
网络请求
-
图片下载
-
文件处理
-
数据存储
-
其他异步执行的任务
查看答案
iOS中实现多线程主要有四种方式- pthread
这个是基于C的线程管理,跨平台,使用复杂,程序员管理,iOS开发中也不会去使用。
- NSThread
这个是基于面向对象操作线程的,使用起来简单。局限性较强,不能设置依赖,当线程开始时候也不能取消线程。线程程序员自己管理,线程之间无法通信。
- GCD
基于C语言封装的线程管理,程序自己管理。基于闭包,使用简单。GCD分为异步执行和同步执行,一个线程分串行和并发两种。GCD常用dispatch_one用于一次执行代码创建单利,dispatch_apply可以异步执行循环,提高执行效率。dispatch_group可以同时异步一组任务等待完成。dispatch_barrier_async通过设置阻断可以让一些线程先执行,一些线程后执行。dispatch_semaphore可以进行数据加锁操作,也可以等待线程处理。dispatch_after可以做延时操作,dispatch_time可以做定时器。
- NSOperation
是基于GCD的封装,面向对象。没有GCD使用方便简单,但是可以添加线程依赖,并且支持线程取消,程序自己管理线程。对于创建的NSOperation添加到NSOperationQueue可以自动异步执行。没有添加直接执行start方法的会在当前线程执行任务。我们通常通过NSOperation的两个子类进行创建,也可以自己创建NSOperation子类自定义来使用。
查看答案
-
performSelector:onThread:withObject:waitUntilDone:方法
-
NSMachPort
查看答案
底层是基于Mach线程实现的查看答案
我们通畅在开发中可以通过下面的集中方案解决线程安全,最简单是使用atomic保证属性访问的线程安全,但是对于可变的数组和字典来说不是线程安全的。还可以通过NSLock进行加锁,可以通过dispatch_semaphore信号量保持线程同步,还可以用@synchronized保障self线程安全。还可以使用POSIX互斥锁来解决线程安全,不太常用。查看答案
如果是基本变量类型是线程安全的,atomic线程安全核心是在属性的set和get方法内部自动加锁。但是只是保证了属性的赋值和获取加锁。但是比如针对于可变的数组和字典,对于数组和字典变更内容没有没有加锁的,所以atomic不是绝对线程安全的。查看答案
这个我们知道多线程实现方案有四种,pthread难用还不如NSTheard明显不行。NSTheard只针对单个线程使用,功能少,线程通信都没。NSOperation这个特点就是依赖和取消线程,明显也不能解决。剩下就只能用GCD来解决了,通过对于GCD的了解,我们可以用dispatch_group和信号量来做。- 利用dispatch_group
dispatch_group_t group = dispatch_group_create();
dispatch_queue_t queue = dispatch_queue_create("dispatch_group", DISPATCH_QUEUE_CONCURRENT);
dispatch_group_async(group, queue, ^{
NSLog(@"下载图片1");
});
dispatch_group_async(group, queue, ^{
NSLog(@"下载图片2");
});
dispatch_group_async(group, queue, ^{
NSLog(@"下载图片3");
});
dispatch_group_async(group, queue, ^{
NSLog(@"下载图片4");
});
dispatch_group_notify(group, queue, ^{
NSLog(@"合成图片完成");
});
- dispatch_barrier_async阻断
dispatch_queue_t queue = dispatch_queue_create("queue", DISPATCH_QUEUE_CONCURRENT);
dispatch_async(queue, ^{
NSLog(@"下载图片1");
});
dispatch_async(queue, ^{
NSLog(@"下载图片2");
});
dispatch_async(queue, ^{
NSLog(@"下载图片3");
});
dispatch_async(queue, ^{
NSLog(@"下载图片4");
});
dispatch_barrier_async(queue, ^{
NSLog(@"合成图片");
});
- dispatch_semaphore信号量
dispatch_queue_t queue = dispatch_queue_create("queue", DISPATCH_QUEUE_CONCURRENT);
dispatch_semaphore_t semaphore = dispatch_semaphore_create(4);
dispatch_async(queue, ^{
NSLog(@"下载图片1");
dispatch_semaphore_signal(semaphore);
});
dispatch_async(queue, ^{
NSLog(@"下载图片2");
dispatch_semaphore_signal(semaphore);
});
dispatch_async(queue, ^{
NSLog(@"下载图片3");
dispatch_semaphore_signal(semaphore);
});
dispatch_async(queue, ^{
NSLog(@"下载图片4");
dispatch_semaphore_signal(semaphore);
});
dispatch_async(queue, ^{
for (NSUInteger i = 0; i < 4; i ++) {
dispatch_semaphore_wait(semaphore, DISPATCH_TIME_FOREVER);
}
NSLog(@"合成图片");
});
- NSOperation
NSOperationQueue *queue = [[NSOperationQueue alloc] init];
NSBlockOperation *operation1 = [NSBlockOperation blockOperationWithBlock:^{
NSLog(@"operation1");
}];
NSBlockOperation *operation2 = [NSBlockOperation blockOperationWithBlock:^{
NSLog(@"operation2");
}];
NSBlockOperation *operation3 = [NSBlockOperation blockOperationWithBlock:^{
NSLog(@"operation3");
}];
NSBlockOperation *operation4 = [NSBlockOperation blockOperationWithBlock:^{
NSLog(@"operation4");
}];
NSBlockOperation *operation5 = [NSBlockOperation blockOperationWithBlock:^{
NSLog(@"operation5");
}];
[operation5 addDependency:operation1];
[operation5 addDependency:operation2];
[operation5 addDependency:operation3];
[operation5 addDependency:operation4];
[queue addOperations:@[operation1,operation2,operation3,operation4,operation5] waitUntilFinished:YES];
查看答案
很容易导致死锁查看答案
我们都知道dispatch_one声明一个静态变量。猜测一定是根据静态变量是否初始化来控制后面是否还执行。为了做到对于静态变量访问和修改,我们可以采用信号量等让后面执行的进行等待,之后等第一个运行完毕根据静态变量是否初始化来是否运行任务。查看答案
-
使用dispatch_sync同步的执行代码
-
DISPATCH_QUEUE_SERIAL串行队列
-
dispatch_barrier阻断
-
dispatch_semaphore信号量
-
设置线程数量为1
-
用NSOperation设置串行依赖