Linux复习 / 线程相关----线程概念与控制 Q&A梳理

这篇具有很好参考价值的文章主要介绍了Linux复习 / 线程相关----线程概念与控制 Q&A梳理。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

前言

本篇博客梳理关于线程相关的Q&A,包括了线程概念与线程的控制。若读者也在复习这块知识,或者正在学习这块知识,可以通过这些Q&A检测自己的知识掌握情况。此外,思维导图已经更新至我的gitee,Q&A之外的体系梳理还请移步思维导图。

Q&A


线程概念

Q:线程和进程的区别?(为什么要有线程,从进程的角度说明这个问题)

A:Linux用task_struct结构体描述一个进程,可以说进程 = task_struct + 内存中的数据与代码。而task_struct包含了进程页表、进程地址空间等资源,创建一个进程就需要为它分配这些资源。值得思考的是:分配资源本身就需要消耗资源,进程是否能充分利用分配得到的资源?而且由于进程具有独立性,进程间想要共享或发送数据,就要进行进程间通信,但通信的成本过高,会消耗过多资源,降低系统的性能。

若操作系统只有进程,那么进程就是系统的基本执行流。

  • 要执行不同的程序,就要创建新的进程,但是创建进程会带来资源的消耗,这是其一
  • 若一个进程要使用另一个进程的数据,就要进行进程间通信,通信的代价也是额外资源的消耗,这是其二

为解决以上两个问题(最主要的两个),线程被引入,线程作为进程的一部分,和进程共享进程地址空间(资源),同时解决了进程间通信与反复创建进程带来的资源消耗问题。

Q:Linux是如何设计线程的?

A:学习进程时,我们说:进程 = task_struct + 内存中的数据与代码,这个说法默认了task_struct是进程控制块,也就是说task_struct是为了进程而设计的结构。但是事实并不是这样,准确的说task_struct是Linux中的一个执行流。若一个进程下没有线程(或者说唯一的线程就是自己),此时的进程就是一个执行流。若一个进程下有多个线程,此时的进程就不再是执行流,此时的执行流是进程下的线程,进程是多个执行流的集合。

所以task_struct即不是为进程设计的,也不是为线程设计的,它是为执行流这个概念设计的,你也可以极端点,认为Linux下没有进程与线程的概念,Linux只有执行流的概念。提出进程和线程只是为了更好的理解操作系统。

回到问题,你可以认为Linux只有执行流的概念,它对应的结构体为task_struct。但是为了使多个执行流可以同时使用相同的资源而不冲突,Linux肯定是要对线程进行设计的。我们可以通过if else判断fork的返回值,控制父子进程,使两进程分别执行不同的代码块(函数),从而使它们的函数栈分离,体现在进程地址空间上,两进程就是使用了不同的空间。这样的思想也体现在线程的设计中,Linux设计了thread_struct结构体,其中有一组变量维护了寄存器地址,这些寄存器则维护了一个函数栈。所以,每个线程都享有一个独立的函数栈(地址空间),这样就解决了线程间数据冲突的问题。
Linux复习 / 线程相关----线程概念与控制 Q&A梳理

总结一下:Linux用thread_struct结构体表示线程结构,该结构体中最重要的是一组寄存器地址,这些寄存器维护了线程的函数栈,使线程享有独立的资源,互不冲突。

Q:学习了线程后,你能说说进程和线程最大的区别是什么吗?

A:两者最大的区别就是:承担的职责不同

  • 进程是系统中资源分配的基本单位,系统分配进程地址空间、页表等结构,消耗了大量资源
  • 线程是系统中调度的基本单位,系统分配资源给进程,线程使用进程的一部分资源,以执行任务

进程和线程的比较

Q:线程使用进程的资源,它们之间的所有资源都是共享的吗?有哪些资源不是共享的?

A:

  • 线程独享的资源
  1. 线程ID:需要用不同的线程ID标识同一进程下的不同线程
  2. 一组寄存器与函数栈:为了防止线程之间发送数据冲突,线程需要维护自己的函数栈
  3. errno:每个线程必须独享errno以便在程序崩溃时更快定位错误
  4. 信号屏蔽字:每个线程可以设置自己想要屏蔽的信号
  5. 调度优先级:可以设置线程的优先级以调整线程的执行顺序
  • 线程与进程共享的数据
  1. 文件描述符表:线程和进程打开的文件,彼此都能看到
  2. 信号的递达方式:线程和进程设置的信号递达方式也会彼此影响
  3. 当前工作路径:进程与使用其资源的线程在同一工作路径下运行
  4. 用户id和组id:进程与使用其资源的线程拥有相同的owner和group
Q:线程的优缺点分别是什么?

A:

  • 优点:
  1. 充分使用进程的资源,尽可能的减少不必要进程的创建,提高系统性能
  2. 线程之间数据共享,比起进程间通信,这是一种更高效的通信方式
  3. 创建线程的代价小于进程,因为系统不要为线程分配页表、进程地址空间这样的资源
  4. 切换线程的代价小于进程,因为系统不需要重新加载页表、进程地址空间,只需要重新加载task_struct结构体以及线程的函数栈
  5. 充分利用多处理器的可并行数量
  6. 在含有慢速IO的进程中,可以创建线程等待慢速IO的结束,使进程可以执行其他任务,不必等待慢速IO的结束
  7. 在密集IO的进程中,可以创建多个线程等待IO的结束,使等待时间重叠,有效提高了程序的运行效率
  • 缺点:
  1. 健壮性较差:线程崩溃退出会导致进程的退出
  2. 调试难度大:多线程程序下的错误难以定位

线程操作

Q:线程终止的三种方式分别是什么?

A:

  1. 直接return,不过返回的对象要强转为(void*)
  2. 调用int pthread_exit(void* retval)退出,该函数的参数是一个类型为void*的变量
  3. 调用int pthread_cancel(pthread_t thread)向指定线程发送cancel信号,该线程的返回值为-1
Q:为什么pthread_self()的返回值和LWP不一样?

A:LWP(light weight process),轻量级进程,使用ps -aL可以查看线程的LWP。而pthread_self()的返回值(线程ID)远远大于LWP,其原因是:

  • Linux没有提供线程的操作接口,或者说这些接口不够简便,需要自己设置于管理线程的属性。我们的线程操作基于第三方库,第三方库帮助我们设置与管理线程的属性

  • 第三方库使用struct thread_info结构体存储线程的信息,而这些结构存储在进程地址空间的共享区,线程ID的值就等于这些结构体的首地址

  • 可以通过程序验证,线程ID的值小于栈区地址,大于堆区地址
    Linux复习 / 线程相关----线程概念与控制 Q&A梳理

  • LWP是内核的一个概念,内核用LWP对轻量级进程进行管理

  • 线程ID是地址空间的一个概念,通过线程ID可以找到线程的属性,从而对线程进程管理(这是我们通过线程库对线程的间接管理

Q:为什么要进行线程分离?

A:主线程创建的子线程默认具有joinable属性,若主线程不主动join子线程,会造成资源泄漏与线程句柄的耗尽。线程分离后,主线程不用join子线程,子线程结束,其资源会自动释放。

这个问题也能理解为:为什么要join子线程?两个原因:一个是回收子线程的资源,一个是得到子线程的返回值,前者是必要的,而后者是非必要的。当主线程不再关心子线程的返回信息时,主线程可以主动分离该线程。

Q:为什么要由主线程分离子线程?不能子线程自己分离?

A:这是为了防止一些bug的产生,也是一种编程规范。若子线程调用pthread_detach分离自己,主线程无法确定子线程什么时候被分离,如果主线程在在子线程调用pthread_detach之前调用pthread_join该线程,那么主线程会陷入阻塞,但由于该线程被分离,不会向主线程返回,所以主线程会陷入永久的阻塞,程序因此产生bug。

所以不能让子线程调用pthread_detach分离自己,这会带来一些不确定性。同时我们也要确保主线程不要对将要分离或已经分离的子线程做任何操作。文章来源地址https://www.toymoban.com/news/detail-412972.html

到了这里,关于Linux复习 / 线程相关----线程概念与控制 Q&A梳理的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包赞助服务器费用

相关文章

  • 『Linux』第九讲:Linux多线程详解(一)_ 线程概念 | 线程控制之线程创建 | 虚拟地址到物理地址的转换

    『Linux』第九讲:Linux多线程详解(一)_ 线程概念 | 线程控制之线程创建 | 虚拟地址到物理地址的转换

    「前言」文章是关于Linux多线程方面的知识,讲解会比较细,下面开始! 「归属专栏」Linux系统编程 「主页链接」个人主页 「笔者」枫叶先生(fy) 「枫叶先生有点文青病」「每篇一句」  我与春风皆过客, 你携秋水揽星河。 ——网络流行语,诗词改版 用现在的话来说:我不

    2024年02月04日
    浏览(6)
  • 【Linux驱动开发】013 与gpio相关的OF函数 一、前言

    在上节,我们提供了驱动中gpio子系统相关的API函数,主要用来申请释放gpio、设置gpio输入输出、获取设置gpio的值。 我们进行上述设置的前提是:在驱动程序中需要读取 gpio 属性内容。为此,Linux 内核提供了几个与 GPIO 有关的 OF 函数。 用于统计设备树某个属性里面定义了几个

    2024年02月14日
    浏览(5)
  • C#多线程学习(一) 多线程的相关概念

    什么是进程? 当一个程序开始运行时,它就是一个进程,进程包括运行中的程序和程序所使用到的内存和系统资源。 而一个进程又是由多个线程所组成的。 什么是线程? 线程是程序中的一个执行流,每个线程都有自己的专有寄存器(栈指针、程序计数器等), 但代码区是共享

    2023年04月13日
    浏览(5)
  • 【Python】多线程编程 ① ( 线程相关概念 | 进程 | 线程 | 协程 / 纤程 | 管程 )

    进程 与 操作系统 : 进程 是 操作系统 中 能够独立运行的单元 , 是 操作系统 对 正在运行的 应用程序 的 抽象结构 描述 ; 操作系统 中 运行的每个 应用程序 就是一个进程 ; 一个操作系统中可以运行 多个 进程 ; 每个 应用程序 都会被 操作系统 分配一个 进程 ID ; 多个进程之间

    2024年02月15日
    浏览(9)
  • 【线程概念和线程控制】

    【线程概念和线程控制】

    教材观点是这样的: 线程是一个执行分支,执行力度比进程更细,调度的成本更低。 Linux内核观点: 进程是系统分配资源的基本单位,线程是CPU调度的基本单位。 这两种说法都是正确的,但是我们究竟该如何理解线程呢? 在一个程序里的一个执行路线就叫做线程(thread)。

    2024年02月16日
    浏览(8)
  • cpp多线程(二)——对线程的控制和锁的概念

    cpp多线程(二)——对线程的控制和锁的概念

    这篇文章是笔者学习cpp多线程操作的第二篇笔记,没有阅读过第一篇的读者可以移步此处: Cpp多线程(一)-CSDN博客 如果读者发现我的文章里有问题,欢迎交流哈!   一、如何控制线程呢? c++11在std::this_thread名称空间(显然,这是一个嵌套在大名称空间里的小名称空间)内

    2024年01月20日
    浏览(3)
  • CPU相关概念:物理cpu数、核数、逻辑cpu数,12核20线程实例分析

    CPU相关概念:物理cpu数、核数、逻辑cpu数,12核20线程实例分析

    学习多线程的时候,需要了解CPU和线程的相关概念,但是网上给出的概念让我实际操作时产生了混淆。 本文与其他文章不一样的点在于,解释为什么逻辑CPU数不是核数的2倍(比较新的处理器会有这种情况),能够解答非计算机专业人士的问题。 CPU信息的查询方法参见本文第

    2024年02月13日
    浏览(17)
  • 【Linux】线程-线程概念

    【Linux】线程-线程概念

    实际上,线程是一个进程内部的控制序列,一个程序的一个执行线路就是一个线程。 并且一个进程中至少有一个线程,本质上,一个进程内部如果有多个线程,那么这些线程实际上是指向同一块地址空间的。而不论进程还是线程,从CPU看来都是一个PCB,只是说线程的PCB要比进

    2023年04月25日
    浏览(7)
  • Linux 多线程 ( 多线程概念 )

    Linux 多线程 ( 多线程概念 )

    在一个程序里的一个执行路线叫做线程 thread ),更准确的定义为:“线程是一个进程内部的控制序列\\\"。 一切进程至少有一个执行线程。 线程在进程内部运行,本质上是在进程地址空间中运行。 在linux系统中,CPU看到的PCB比传统的进程更加轻量化。 透过进程虚拟地址空间,可

    2024年02月09日
    浏览(7)
  • Linux之多线程(上)——Linux下的线程概念

    Linux之多线程(上)——Linux下的线程概念

    本文介绍了地址空间和二级页表、Linux下的线程、线程的优缺点以及线程与进程的关系等概念。 地址空间是进程能看到的资源窗口 :一个进程可以看到代码区、堆栈区、共享区、内核区等,大部分的资源是在地址空间上看到的。 页表决定进程真正有用资源的情况 :进程认为

    2024年02月09日
    浏览(8)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包