Linux —— 线程

Linux —— 线程

  • 什么是线程
  • Linux如何实现线程
  • Winodws如何实现线程
  • 使用一下线程
    • pthread_create
      • 函数原型
      • 参数说明
      • 返回值
    • 如何解决
  • ps -aL 查看线程
  • 线程为什么轻量

我们今天进入线程的学习:

什么是线程

我们先来了解一个笼统的概念:简单来说,线程(Thread)是操作系统能够进行运算调度的最小单位

这句话其实很抽象,我们来画个图来分析一下:

首先我们知道进程
在这里插入图片描述
然后,我们可以在此基础上,如果可以让多个PCB指向一个进程空间,可以提高执行效率:
在这里插入图片描述
然后,我们称红色的为线程
在这里插入图片描述
这里我们可以得到这样几个事实(概念):

  1. 进程是资源分配的基本单位,因为只有进程会有进程地址空间,才会运行。
  2. 线程是在进程类的,是进程的小弟,帮进程做事,自己和进程共享进程地址空间。

这个时候,我们再来看看线程的概念:

线程(Thread)是操作系统能够进行运算调度的最小单位它是进程内部的一个执行序列,代表了进程中一个单一的顺序控制流一个进程可以包含一个或多个线程,这些线程共享所属进程的内存空间和资源,比如代码段、数据段、文件句柄等,但每个线程都拥有自己的程序计数器、栈空间(调用栈)、寄存器组等执行上下文,以实现独立的执行路径。
线程的存在使得程序能够并发执行不同的任务,提高了程序的执行效率和响应速度,特别是在多核处理器系统中,多个线程可以同时在不同的CPU核心上运行,实现真正的并行处理。线程之间的协作和数据共享相对灵活,但同时也引入了资源竞争和同步问题,需要通过互斥锁、信号量等机制来解决潜在的竞态条件和死锁问题。
线程分为两类:内核线程(Kernel Thread)用户线程(User Thread)。内核线程直接由操作系统内核管理,其创建、调度和切换等操作都是在内核层面完成的;用户线程则由应用程序管理,有时需要借助于内核线程来实现多线程的并行执行。在某些系统中,还存在混合模式,如N:1模型(多个用户线程映射到一个内核线程)或M:N模型(多个用户线程映射到多个内核线程),以平衡用户态与内核态切换的成本和线程管理的灵活性。

Linux如何实现线程

Linux在实现线程上面偷了懒,并没有专门实现,而是对照进程:

Linux 实现线程的概念确实借鉴了进程的实现方式。在Linux内核中,没有专门的“线程”这一概念,而是将线程作为轻量级进程(Lightweight Processes, LWP)来处理。这意味着每个线程在内核中都表现为一个标准的进程,拥有自己的 task_struct,这是Linux内核中表示进程的核心结构体。然而,这些线程之间共享某些资源,如地址空间、文件描述符和信号处理等,这与传统意义上的独立进程不同。
Linux使用 clone() 系统调用来创建线程,该调用允许父子进程共享某些资源,同时保持独立的执行流和少量独立的状态,如线程ID、栈等。通过精心选择 clone() 的参数,可以创建具有不同资源共享级别的新执行实体,从而实现线程。通常,线程库如POSIX threads (pthreads) 会封装 clone() 系统调用,为程序员提供更高层次的线程创建和管理接口。

因此,可以说Linux中的线程实现是基于进程概念的扩展,利用了进程的基础设施并加以调整,以支持在同一进程内的多个执行流,同时保持高效的资源复用。

Winodws如何实现线程

Wnidows是专门实现了线程的概念:

是的,Windows操作系统实现了线程的概念。在Windows中,线程是执行代码的基本单位,而进程则是资源分配的最小单位,每个进程可以包含一个或多个线程。Windows通过一系列线程相关的API来支持线程的创建、管理和调度,这些API允许开发者创建、终止线程,设置线程的优先级,进行线程同步,以及管理线程的执行状态。
例如,使用CreateThread或更现代且功能更全面的CreateThreadEx函数可以创建一个新的线程;ExitThread用于结束一个线程;WaitForSingleObjectWaitForMultipleObjects可以用来同步线程;而SetThreadPriority可以改变线程的优先级等。此外,Windows还提供了线程局部存储、互斥量、信号量、事件等机制来帮助开发者管理线程间的通信和同步问题。

总之,Windows通过其内核对象和用户模式API全面支持了线程的概念,并且在设计上确保了线程能够在多处理器系统上有效地并行执行。

使用一下线程

我们可以使用一下线程的接口:
在这里插入图片描述

pthread_create

pthread_create函数是POSIX线程库(Pthreads)中的一个核心函数,用于在UNIX-like系统(如Linux、macOS等)中创建一个新的线程。这个函数允许程序实现多线程并发执行,提高执行效率和响应速度。以下是pthread_create函数的基本信息和用法:

函数原型

int pthread_create(pthread_t *restrict tidp,const pthread_attr_t *restrict attr,void *(*start_rtn)(void *), void *restrict arg);

参数说明

  • tidp: 指向线程标识符(pthread_t类型)的指针,用于存储新创建线程的标识。成功创建后,线程的ID将被写入此地址。
  • attr: 一个指向pthread_attr_t结构的指针,该结构可以用来设置线程的属性,如栈大小、调度策略等。如果为NULL,则使用默认属性。
  • start_rtn: 指向线程开始执行的函数的指针,也就是线程的入口点。这个函数必须接收一个void *类型的参数,并返回一个void *类型的指针。
  • arg: 传递给线程入口函数的参数,类型为void *。在线程启动时,这个参数会被传递给start_rtn函数。

返回值

  • 如果成功创建线程,pthread_create返回0。
  • 如果出现错误(比如资源不足),则返回一个非零的错误码。
#include<iostream>
#include<unistd.h>
#include<pthread.h>// 线程函数,打印线程信息
void *ThreadRountine(void* arg)
{const char *thread_name = (const char*)arg; // 将参数转换为字符串while(true) // 无限循环{std::cout << "I am a thread process" << ",pid: "<< getpid()<< std::endl; // 打印线程信息sleep(1); // 休眠1秒}
}int main()
{pthread_t tid; // 定义线程ID// 创建线程,传入线程函数和参数pthread_create(&tid,nullptr,ThreadRountine,(void*)"thread 1");while(true) // 无限循环{std::cout << "I am the main thread"<< ",pid: "<< getpid()<< std::endl; // 打印主线程信息sleep(1); // 休眠1秒}return 0;
}

在这里插入图片描述

我们发现运行起来了,但是很乱,这是因为主线程和创建的子线程都在同时尝试向标准输出(stdout)写入内容,而std::cout的输出默认是非原子性的,即输出操作可以被其他线程中断。当多个线程并发写入时,它们可能交错打印,导致输出混乱

如何解决

上面的问题就是竞争,线程竞争我们在学习操作系统中,已经学习过许多方法,这里我们用来解决:

#include <iostream>
#include <pthread.h>
#include <unistd.h>
#include <mutex> // 引入互斥锁std::mutex cout_mutex; // 全局互斥锁实例void *ThreadRoutine(void *arg) 
{const char *thread_name = (const char *)arg;while (true) {std::unique_lock<std::mutex> lock(cout_mutex); // 锁定互斥锁std::cout << "I am a thread process" << ", pid: " << getpid() << std::endl;lock.unlock(); // 解锁sleep(1);}
}int main() 
{pthread_t tid;pthread_create(&tid, nullptr, ThreadRoutine, (void *)"thread 1");while (true) {std::unique_lock<std::mutex> lock(cout_mutex); // 锁定互斥锁std::cout << "I am the main thread" << ", pid: " << getpid() << std::endl;lock.unlock(); // 解锁sleep(1);}return 0;
}

在这里插入图片描述

ps -aL 查看线程

引入线程之后,我们用ps -ajx查不出具体的区别:
在这里插入图片描述这个时候,我们要用ps -aL 查看线程
在这里插入图片描述
上面的LWP(Light Weight Process)就是线程,这里我们看到除了进程的13091,还有一个线程13902属于13901。

线程为什么轻量

线程之所以被称为轻量级进程(Lightweight Process),是因为相比于传统的进程,线程在以下几方面显著地减少了资源消耗和管理开销,从而显得更为轻量:

  1. 共享资源:线程间共享同一个进程的地址空间,包括代码段、数据段以及堆空间。这意味着线程不需要为每个线程复制一份程序代码和全局变量,大大节省了内存资源。
  2. 上下文切换:线程之间的上下文切换比进程更快。因为它们共享同一地址空间,内核在切换时不需要保存和恢复整个地址空间的内容,只需要保存和恢复线程特有的上下文信息,如寄存器状态、栈指针等。
  3. 创建销毁:创建和销毁线程的代价低于进程。由于减少了资源分配的需求,线程的创建速度通常快于进程。同样,销毁线程时,只需释放它独有的资源(如栈空间),而不必回收整个地址空间。
  4. 通信成本:线程间通信更高效。由于共享内存空间,线程可以直接读写同一块内存区域来交换数据,而不需要通过复杂的进程间通信(IPC)机制,如管道、套接字等。
  5. 调度开销:线程的调度通常由同一进程内的线程库或操作系统内核直接管理,而不需要像进程那样涉及更复杂的权限检查和资源分配,因此调度成本较低。

综上所述,线程在资源使用、上下文切换、创建销毁、通信及调度等方面相比进程更加高效,故被形象地称为轻量级进程。这种轻量化使得线程成为实现并发执行、提高程序性能和响应速度的有效手段。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/326075.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

【计算机网络篇】数据链路层(8)共享式以太网的退避算法和信道利用率

文章目录 &#x1f6f8;共享式以太网的退避算法&#x1f95a;截断二进制指数算法 &#x1f354;共享式以太网的信道利用率 &#x1f6f8;共享式以太网的退避算法 在使用CSMA/CD协议的共享总线以太网中&#xff0c;正在发送帧的站点一边发送帧一边检测碰撞&#xff0c;当检测到…

Mysql进阶-sql优化篇

sql优化 sql优化insert优化批量插入手动提交事务主键顺序插入大批量插入数据 主键优化数据组织方式页分裂页合并主键设计原则 order by 优化原则 group by优化limit优化count 优化count的几种用法 update优化 sql优化 insert优化 批量插入 Insert into tb_test values(1,Tom…

百信银行的喜和忧:业绩与不良规模同增,曾因踩红线被罚500万元

近日&#xff0c;有报道指出&#xff0c;陪伴中信百信银行股份有限公司&#xff08;下称“百信银行”&#xff09;走过七年光阴的首任行长李如东已离任&#xff0c;离任原因或与“7年轮岗”监管规定有关。作为替代&#xff0c;中信银行科技信息部总经理寇冠出任百信银行行长。 …

【高阶数据结构(三)】图的遍历最小生成树问题

&#x1f493;博主CSDN主页:杭电码农-NEO&#x1f493;   ⏩专栏分类:高阶数据结构专栏⏪   &#x1f69a;代码仓库:NEO的学习日记&#x1f69a;   &#x1f339;关注我&#x1faf5;带你学习更多Go语言知识   &#x1f51d;&#x1f51d; 高阶数据结构 1. 前言2. 图的遍…

Android Compose 一:基础控件

Flutter 与 Compose 组件辣么像&#xff0c;难道是同一个google团队整的&#xff1b;也未深究&#xff0c;只是猜测。 创建项目 需要使用新版本Android studio&#xff0c;忽略步骤… 项目目录 MainActivity说明 1 系统默认页面 Preview 修饰的方法&#xff0c;只用来供开发…

【Linux】-Linux用户和权限与权限的修改[3]

目录 一、认知root用户 1、root用户&#xff08;超级管理员&#xff09; 2、su和exit命令 3、sudo命令 二、用户、用户组管理 1、用户管理 2、getent 三、查看权限控制 1、认知权限信息 四、修改权限控制 - chmod 五、修改权限控制 - chown 一、认知root用户 1、root…

C#调用电脑摄像头拍照

1.打开VS2019&#xff0c;新建一个Form窗体&#xff0c;工具->NuGet包管理工具->管理解决方案的NuGet包&#xff0c;在浏览里搜索AForge.Controls、AForge.Video.DirectShow&#xff0c;安装AForge.Controls和AForge.Video.DirectShow 2.安装AForge组件完成后&#xff0c…

Spring底层入门(十一)

1、条件装配 在上一篇中&#xff0c;我们介绍了Spring&#xff0c;Spring MVC常见类的自动装配&#xff0c;在源码中可见许多以Conditional...开头的注解&#xff1a; Conditional 注解是Spring 框架提供的一种条件化装配的机制&#xff0c;它可以根据特定的条件来控制 Bean 的…

如何快速提取出一个文件里面全部指定类型的文件的全部路径

首先&#xff0c;需要用到的这个工具&#xff1a; 度娘网盘 提取码&#xff1a;qwu2 蓝奏云 提取码&#xff1a;2r1z 打开工具&#xff0c;切换到第五个模块&#xff0c;文件批量复制模块&#xff08;快捷键&#xff1a;Ctrl5&#xff09; 点击右边的“搜索添加”按钮&#…

[windows系统安装/重装系统][step-2]BIOS设置UEFI引导、磁盘分区GPT分区、安装系统[含完整操作拍照图片]

重装系统三部曲 [windows系统安装/重装系统][step-1]U盘启动盘制作&#xff0c;微软官方纯净系统镜像下载-CSDN博客 [windows系统安装/重装系统][step-2]BIOS设置UEFI引导、磁盘分区GPT分区、安装系统[含完整操作拍照图片]-CSDN博客 [windows系统安装/重装系统][step-3]装驱动…

开源免费的定时任务管理系统:Gocron

Gocron&#xff1a;精准调度未来&#xff0c;你的全能定时任务管理工具&#xff01;- 精选真开源&#xff0c;释放新价值。 概览 Gocron是github上一个开源免费的定时任务管理系统。它使用Go语言开发&#xff0c;是一个轻量级定时任务集中调度和管理系统&#xff0c;用于替代L…

使用Android数据恢复恢复已删除的文件[Windows]

智能手机或平板电脑等 Android 设备为用户提供了发送、接收、处理和存储各种数据的能力。它提供了传统手机无法实现的多功能性和简化功能。即便如此&#xff0c;您管理存储在安卓设备中的数据的方式完全取决于您。如果您的手机出现问题&#xff0c;例如系统崩溃或操作系统更新失…

Python-VBA函数之旅-sum函数

目录 一、sum函数的常见应用场景 二、sum函数使用注意事项 三、如何用好sum函数&#xff1f; 1、sum函数&#xff1a; 1-1、Python&#xff1a; 1-2、VBA&#xff1a; 2、推荐阅读&#xff1a; 个人主页&#xff1a; https://myelsa1024.blog.csdn.net/ 一、sum函数的常…

2024.5.19 机器学习周报

引言 Abstract 文献阅读 1、题目 X-HRNET: TOWARDS LIGHTWEIGHT HUMAN POSE ESTIMATION WITH SPATIALLY UNIDIMENSIONAL SELF-ATTENTION 2、引言 高分辨率表示是人体姿态估计实现高性能所必需的&#xff0c;随之而来的问题是高计算复杂度。特别地&#xff0c;主要的姿态估…

外网如何访问内网?快解析

由于公网IP资源短缺&#xff0c;我们的电脑大多处于内网环境&#xff0c;如何在外网访问内网电脑&#xff0c;成为一个令人头疼的问题&#xff0c;下面我给大家推荐一个非常实用的方法。 1&#xff1a;访问快解析下载安装快解析服务器 2&#xff1a;运行软件&#xff0c;点击“…

ASP.NET MVC(二) HtmlHelper

强类型 》》》 Form Html.Action() 执行一个Action&#xff0c;并返回html字符串。 Html.ActionLink() 生成一个超链接。 》》》 htmlhelper 扩展方法 /// 扩展方法 三要素 静态类静态方法this 》》》》上面需要引入命名空间&#xff0c; 》》》 不需要引入命名空间 pu…

systrace使用

systrace使用 chrome://tracing/ 抓trace方法 1.脚本 在sdk/platformtools/systrace文件目录下执行&#xff1a; python2 systrace.py -b 32000 -o setting_qian.html gfx input view webview wm am audio video camera app ss sched irq freq idle disk load sync workq reg…

Sublime Text for Mac:强大的文本编辑器

Sublime Text for Mac&#xff0c;一款轻量而强大的文本编辑器&#xff0c;为您的编程和写作工作带来无限可能。它以其简洁的界面和出色的性能&#xff0c;成为Mac用户中备受推崇的编辑器之一。 Sublime Text支持多种编程语言&#xff0c;无论是Python、JavaScript、HTML还是CS…

GNSS地表位移监测仪的工作原理

TH-WY1GNSS地表位移监测仪是一种用于实时监测地表位移变化的仪器设备。它主要利用全球导航卫星系统(GNSS)或全球定位系统(GPS)技术&#xff0c;通过接收卫星信号来测量地表点位的移动变化&#xff0c;从而获取地表点位的精确坐标信息&#xff0c;进而监测地表的水平和垂直位移情…

基于微信小程序的预约挂号系统(源码)

博主介绍&#xff1a;✌程序员徐师兄、10年大厂程序员经历。全网粉丝12W、csdn博客专家、掘金/华为云/阿里云/InfoQ等平台优质作者、专注于Java技术领域和毕业项目实战✌ &#x1f345;文末获取源码联系&#x1f345; &#x1f447;&#x1f3fb; 精彩专栏推荐订阅&#x1f447…