Linux下的线程
1.什么是线程
- 在一个程序里的一个执行路线就叫做线程(thread);
- 一切进程至少都有一个执行线程;
- 线程在进程内部运行,本质是在进程地址空间内运行;
多线程的处理思路:一个运行中的程序中,具有多个执行流,各自完成一个功能模块的实现。
解释一下:
1、进程就是一个运行中的程序,操作系统会创建一个pcb (运行中程序的描述),并且分配资源,通过pcb来调度运行这个程序。
2、线程是一个进程中的执行流,但是linux下实现进程中的执行流的时候,使用了pcb实现;
3、因此就说linux下的线程是一个pcb, 称作轻量级进程,因为同一个进程中的线程共用进程分配的资源;
5.而进程就是所有线程的统称,就是一个线程组, 系统在运行程序,分配资源的时候是分配给线程组,分配给整个进程的。
进程是资源分配的基本单位,线程是cpu调度的基本单位。(进程就像是一个工厂,线程就是工厂里干活的工人)
一个运行中的程序就是一个进程, 以前我们所说的进程,这时候再来理解,就是具有一个线程的进程,linux 下的线程是一个pcb (轻量级进程), 是一个进程中的一条执行流;
这时候再来理解进程的话:进程就是一个线程组;
2.线程之间的独有与共享
vfork-创建出来的子进程与父进程共用同一个虚拟地址空间,但是父进程会阻塞,因为同时运行会出现栈混乱。
线程是一个pcb;一个进程中若有多个线程,也就意味着有多个pcb,这些pcb共用同一个虚拟地址空间;
它是如何做到同时运行而不会出现栈混乱的情况的呢?
线程之间的独有与共享:
独有:
- 栈(每个线程一个,就可以避免出现栈混乱了);
- 寄存器(每一个pcb都是一个执行流) ;
- 信号屏蔽字(阻塞自己想阻塞的信号);
- errno (每调用一次系统调用都会重置errno)。
共享:
- 代码段和数据段(虛拟地址空间);
- 信号的处理方式;
- I0信息;
- 工作路径;
- 用户id;
- 组id;
3、优缺点
多线程与多进程都能进行多任务处理,我们以后写代码的时候就要根据各自的优缺点以及应用场景来选择技术:
多线程任务处理相较于多进程的优点:
1、线程间的通信更加灵活方便(除了进程间通信方式以外,还可以通过全局变量 / 函数传参实现通信);
2、线程的创建和销毁成本更低(线程间共享进程等的大部分资源);
3、同一个进程中的线程间调度成本更低(切换页表,数据);
4、线程的执行粒度更加细致。
缺点:
-
线程间缺乏访问控制,有些系统调用(exit)或者异常是针对整个进程产生效果;
-
多线程任务处理没有多进程任务处理稳定性高;
4、应用场景:
**1、**多进程应用场景,对主程序的稳定性安全性要求更高的场景,比如shell / 网络服务器;
**2、**多进程 / 多线程进行多任务的并发处理的共同优势:
- I0密集型程序:程序中大部分的工作都是进行I0,占用cpu极少;
可以在一个执行流中发起一个IO;避免了以前只有一个执行流时,只有一个I0完成了之后才能进行下一个情况,提高了IO效率。(并行压缩了IO等待时间)。
- cpu密集型程序:程序中的大部分工作都是进行数据运算。
在cpu密集型程序中,执行流的创建并不是越多越好,多了反而会提高cpu调度的成本
cpu密集型程序中,线程的创建最好是cpu核心数+1。
5、 进程与线程的选择取决以下几点:
1、需要频繁创建销毁的优先使用线程;因为对进程来说创建和销毁一个进程代价是很大的。
2、线程的切换速度快,所以在需要大量计算,切换频繁时用线程,还有耗时的操作使用线程可提高应用程序的响应。
3、因为对CPU系统的效率使用上线程更占优,所以可能要发展到多机分布的用进程,多核分布用线程;
4、并行操作时使用线程,如C/S架构的服务器端并发线程响应用户的请求;
5、需要更稳定安全时,适合选择进程;需要速度时,选择线程更好。
6、线程进程的区别体现在几个方面:
1、地址空间和其它资源(如打开文件):进程间相互独立,同一进程的各线程间共享; 某进程内的线程在其它进程不可见。
2、通信:进程间通信IPC(管道,信号量,共享内存,消息队列),线程间可以直接读写进程数据段(如全局变量)来进行通信------需要进程同步和互斥手段的辅助,以保证数据的一致性。
3、调度和切换:线程上下文切换比进程上下文切换要快得多。
7.总结一哈:(什么是进程,什么是线程)
- 进程是指在系统中正在运行的一个应用程序,程序一旦运行就是进程,进程可以认为是程序执行时的一个实例。进程是系统进行资源分配的独立实体, 且每个进程拥有独立的地址空间。一个进程无法直接访问另一个进程的变量和数据结构, 如果希望让一个进程访问另一个进程的资源,需要使用进程间通信,比如:管道,文件, 套接字等。
- 一个进程可以拥有多个线程,每个线程使用其所属进程的栈空间。 线程与进程的一个主要区别是,同一进程内的多个线程会共享部分状态, 多个线程可以读写同一块内存(一个进程无法直接访问另一进程的内存)。同时,每个线程还拥有自己的寄存器和栈,其它线程可以读写这些栈内存。线程是进程的一个实体,是进程的一条执行路径。线程是进程的一个特定执行路径。当一个线程修改了进程中的资源, 它的兄弟线程可以立即看到这种变化。