进程、线程、协程的总结

学习 程序员小灰 - 一文讲透 “进程、线程、协程”的笔记记录

进程

程序本身是没有生命周期的,它只是存在磁盘上的一些指令,程序一旦运行就是进程

进程是-操作系统 提供的 抽象概念,是系统进行 资源分配和调度的 基本单位(出现线程以后,调度的基本单位就是线程),是操作系统结构的基础。程序是指令、数据及其组织形式的描述,进程是程序的实体

当程序需要运行时,OS 将代码所有静态数据记载到内存和进程的地址空间(每个进程都拥有唯一的地址空间)中,通过创建和初始化栈(局部变量,函数参数和返回地址)、分配堆内存以及与IO相关的任务;当前期准备工作完成,启动程序,OS 将 CPU 的控制权转移到新创建的进程,进程开始运行。

一个进程至少有五种基本状态:

  • 初始态:进程刚被创建,准备其他系统资源
  • 就绪态:所有所需资源已准备完成,等待被调度CPU资源
  • 运行态:执行状态
  • 阻塞态:进程等待某件事情完成
  • 终止态:进程结束

进程、线程、协程的总结

CPU资源上进程间的切换,被称为上下文切换(context switch)。涉及到:

  • 保存当前进程的上下文
  • 恢复新进程的上下文

分配、回收系统资源;
更新 PCB 中的信息;
PCB 放入合适的队列;

进程间的数据共享

系统中的 进程 与其他 进程 共享 CPU和主存资源,为了更好的管理主存,现在系统提供了一种对主存的抽象概念,即为虚拟存储器(VM)。它是一个抽象的概念,它为每一个进程提供了一个假象:即每个进程都在独占地使用主存。

虚拟存储器主要提供了三个能力:

  1. 将主存看成是一个存储在磁盘上的高速缓存,在主存中只保存活动区域,并根据需要在磁盘和主存之间来回传送数据,通过这种方式,更高效地使用主存

  2. 为每个进程提供了一致的地址空间,从而简化了存储器管理

  3. 保护了每个进程的地址空间不被其他进程破坏(映射)

进程、线程、协程的总结

线程

线程-也是操作系统提供的抽象概念,是程序执行流的最小单元,是 处理器调度和分派的基本单位。一个进程可以有一个或多个线程,同一进程中的多个线程将共享该进程中的全部系统资源,如虚拟地址空间,文件描述符和信号处理等等。但同一进程中的多个线程有各自的调用栈和线程本地存储(如下图所示)。

OS 会为线程分配一个线程控制块TCB(Thread Control Block),将所有用于控制和管理线程的信息记录在线程的控制块中,TCB中通常包括:

  • 线程标志符
  • 一组寄存器
  • 线程运行状态
  • 优先级
  • 线程专有存储区(堆、栈)
  • 信号屏蔽

进程与线程的区别

  • 进程是资源的分配和调度的独立单元。进程拥有完整的虚拟地址空间,当发生进程切换时,不同的进程拥有不同的虚拟地址空间。而同一进程的多个线程是可以共享同一地址空间

  • 线程是CPU调度的基本单元,一个进程包含若干线程。

  • 线程比进程小,基本上不拥有系统资源。线程的创建和销毁所需要的时间比进程小很多

  • 由于线程之间能够共享地址空间,因此,需要考虑同步和互斥操作

  • 一个线程的意外终止会影响整个进程的正常运行,但是一个进程的意外终止不会影响其他的进程的运行。因此,多进程程序安全性更高。

总之,多进程程序安全性高,进程切换开销大,效率低;多线程程序维护成本高,线程切换开销小,效率高。

协程

协程(Coroutine,又称微线程)是一种 比线程更加轻量级 的存在,协程不是被操作系统内核所管理,而完全是由程序所控制。协程与线程以及进程的关系见下图所示。

  • 协程可以比作子程序,但执行过程中,子程序内部可中断,然后转而执行别的子程序,在适当的时候再返回来接着执行。协程之间的切换不需要涉及任何系统调用或任何阻塞调用

  • 协程只在一个线程中执行,子程序之间的切换发生在用户态上,而线程的阻塞状态是由操作系统内核来完成,发生在内核态上,因此协程相比线程节省线程创建和切换的开销

  • 协程中不存在同时写变量冲突,因此,也就不需要用守卫关键区块的同步性原语,比如互斥锁、信号量等,并且不需要来自操作系统的支持。

进程、线程、协程的总结


线程之间是如何进行协作的呢?

最经典的例子是生产者/消费者模式,即若干个生产者线程向队列中系欸如数据,若干个消费者线程从队列中消费数据。
进程、线程、协程的总结