【手撕C语言】多线程

  • (꒪ꇴ꒪ ),Hello我是祐言QAQ
  • 我的博客主页:C/C++语言,Linux基础,ARM开发板,软件配置等领域博主🌍
  • 快上🚘,一起学习,让我们成为一个强大的攻城狮!
  • 送给自己和读者的一句鸡汤🤔:集中起来的意志可以击穿顽石!
  • 作者水平很有限,如果发现错误,可在评论区指正,感谢🙏

一、概念解析

1.什么是C语言线程?

        C语言是一种面向过程的编程语言,不像Java等高级语言内置了线程类和库。C语言通过调用操作系统提供的线程库来实现多线程编程。在C语言中,线程是进程内的执行单元,一个进程可以包含多个线程,它们共享进程的资源,但拥有独立的栈空间。

2.C语言中的线程库

        C语言中通常使用POSIX线程库(也称为pthread库)来进行多线程编程。POSIX线程库是一个跨平台的线程库,提供了创建、同步和销毁线程的函数。在Linux、macOS等UNIX-like系统中,该库已经内置,而在Windows系统中可以通过一些第三方库或者编译器特定的选项来支持。

3.多线程的优势

  • 提高程序的并发性:多线程允许程序同时执行多个任务,从而提高程序的并发性和响应性。
  • 充分利用多核处理器:多线程可以在多核处理器上并行执行,充分利用硬件资源。
  • 支持异步编程:线程可以用于执行耗时的操作,如I/O操作,而不会阻塞主线程的执行。

4.多线程的挑战

  • 竞态条件:多个线程同时访问和修改共享资源可能导致数据不一致和意料之外的结果。
  • 死锁:多个线程因为互相等待对方释放资源而陷入无限等待的状态。
  • 内存管理:需要小心处理线程间的内存分配和释放,以避免内存泄漏和悬空指针等问题。

二、 线程的创建

        创建一个线程就像定义一个函数一样,我们只需要搞清楚创建线程的四个参数:thread,attr,start_routine,arg,分别是什么,怎么用就足够。

#include <pthread.h>        //线程函数的头文件int pthread_create(pthread_t *thread, const pthread_attr_t *attr,void *(*start_routine) (void *), void *arg);thread:线程id,唯一标识一条线程
attr:设置为NULL
start_routine:线程的任务函数
arg:线程任务函数的参数

        另外要强调的是:-pthread     //使用线程函数时,需要链接这个库!!!

三、线程的取消


        其实就是给线程一个取消请求,一般情况下,线程会默认收到取消请求。

int pthread_cancel(pthread_t thread);

四、例程

        下面是一个简单的例子,让我们更好的理解线程如何使用:

#include <stdio.h>
#include <pthread.h>
#include <unistd.h>// 线程共享全局变量
int g_a = 100;void *task (void *arg)
{while(1){sleep(1);printf("task....%s-->%d\n", (char *)arg, g_a);}
}// main本身就是一个线程
int main(void)
{pthread_t tidA, tidB;// 创建一条新的线程,新的线程所要执行的任务就是task所指向的函数里面的逻辑pthread_create(&tidA, NULL, task, (void *)"A");pthread_create(&tidB, NULL, task, (void *)"B");// task(NULL);while(1){sleep(1);printf("main....\n");g_a++;if(g_a == 110)pthread_cancel(tidA);	//给tidA线程发送一个取消请求if(g_a == 115)pthread_cancel(tidB);	//给tidB线程发送一个取消请求}return 0;
}

 

        这段C语言代码是一个简单的多线程示例,它展示了如何使用pthread库来创建和管理线程,并演示了线程之间共享全局变量的情况。

  1. 首先,全局变量g_a被定义为整数类型并初始化为100。

  2. task函数是一个线程的执行体,它通过传递一个参数arg来区分不同的线程。该函数使用无限循环(while循环),每隔一秒打印一次task....并输出线程标识符("A"或"B")以及全局变量g_a的值。

  3. main函数是程序的入口,也是主线程。它做了以下事情:

    • 创建两个新的线程(tidA和tidB),每个线程都执行task函数。线程tidA被标记为"A",线程tidB被标记为"B",通过传递参数给task函数来区分它们。
    • 在主线程中,使用无限循环(while循环)来打印"main....",并且每秒增加全局变量g_a的值。
    • 当全局变量g_a的值等于110时,主线程发送一个取消请求给线程tidA,使得线程tidA会终止(退出)。
    • 当全局变量g_a的值等于115时,主线程发送一个取消请求给线程tidB,使得线程tidB会终止(退出)。

        需要注意的是,取消请求是一种请求终止线程的方式,但并不能保证线程会立即终止,具体是否终止取决于线程的处理逻辑。

        更多C语言Linux系统ARM板实战数据结构相关文章,关注专栏:

   手撕C语言

            玩转linux

                    脚踢数据结构

                            6818(ARM)开发板实战

📢写在最后

  • 今天的分享就到这啦~
  • 觉得博主写的还不错的烦劳 一键三连喔~
  • 🎉感谢关注🎉

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

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

相关文章

SpringMVC注解配置

1xml配置方式&#xff08;配置文件注解的方式&#xff09; 前提导入相关依赖&#xff1a;pom文件 说明&#xff1a;下方依赖是ssm项目中较为常用的一部分&#xff0c;可能部分依赖对于springmvc配置并未有关系&#xff0c;根据自己需求添加和删除。 <dependencies> &l…

Android 13 Hotseat定制化修改——001 hotseat布局方向

目录 一.背景 二.hotseat布局方向 一.背景 由于需求是需要自定义修改Hotseat,所以此篇文章是记录如何自定义修改hotseat的,应该可以覆盖大部分场景,修改点有修改hotseat布局方向,hotseat图标数量,hotseat图标大小,hotseat布局位置,hotseat图标禁止形成文件夹,hotseat图…

web-xss

一、简介 XSS 又称CSS(Cross Site Scripting)或跨站脚本攻击&#xff0c;攻击者在网页中插入由JavaScript编写的恶意代码&#xff0c;当用户浏览被嵌入恶意代码的网页时&#xff0c;恶意代码将会在用户的浏览器上执行。 二、xss的攻击方式 Dom&#xff1a;这是一种将任意 Jav…

质检工具(FindBugs、CheckStyle、Junit、Jmeter、Apifox)

1、Findbugs IDEA软件中可以装该插件,2018版本以前主要搜索FindBugs-IDEA 、2018版本以后主要搜索 SpotBugs。 1.1、FindBugs-IDEA安装及使用流程: 1.2、SpotBugs安装及使用流程: 2、Checkstyle IDEA软件中可以装该插件,所有版本的插件一致:CheckStyle 2.1、安装流程…

【Linux】内核宏定义解释postcore_initcall,arch_initcall,subsys_initcall

postcore_initcall postcore_initcall(pcibus_class_init) 是一个宏&#xff0c;用于在Linux内核初始化过程中注册一个后期初始化函数。 这个宏的含义如下&#xff1a; postcore_initcall 是一个宏定义&#xff0c;用于指定注册的函数在内核初始化的哪个阶段执行。 pcibus_cl…

Nacos服务治理—负载均衡

引入负载均衡 在消费方引入负载均衡机制&#xff0c;同时简化获取服务提供者信息的流程 Spring Cloud引入组件LoadBalance实现负载均衡 添加依赖 <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web<…

安卓应用面试

Cordova 说明&#xff1a;一个移动框架&#xff0c;将HTML&#xff0c;CSS&#xff0c;JS封装为原生APP(hybird) 优点&#xff1a;跨平台&#xff0c;利于移植&#xff0c;能利用HTML5的各种特性&#xff0c;快速开发&#xff0c;成本低 缺点&#xff1a;不能使用设备的所以…

查看CentOS版本及系统位数与设置CentOS 7.9 2009 防火墙配置放开端口的命令与过程

一、查看CentOS版本及系统位数 1.1 命令汇总 //1、安装redhat-lsb yum install -y redhat-lsb//2、查看系统版本信息 lsb_release -a //3、查看系统位数 getconf LONG_BIT1.2 截图 二、设置CentOS7.9 2009 防火墙配置放开端口 2.1 命令汇总 //禁止防火墙开机启动。这种方法方…

.netcore grpc客户端流方法详解

一、客户端流式处理概述 客户端流式处理方法在该方法没有接收消息的情况下启动。 requestStream 参数用于从客户端读取消息。 返回响应消息时&#xff0c;客户端流式处理调用完成。客户端可以发送多个消息流到服务端&#xff0c;当所有客户端消息流发送结束&#xff0c;调用请…

libheif —— 2、编写苹果、小米的.heic图片查看器

效果图 .heic简介 HEIC&#xff0c;是iOS 11更新后&#xff0c;iPhone 7及其后硬件&#xff0c;在拍摄照片时的默认图像存储格式。 HEIC是一种图像格式&#xff0c;上线时间还比较短&#xff0c;只有4年左右。自iOS 11和macOS High Sierra&#xff08;10.13&#xff09;内测开始…

16-2_Qt 5.9 C++开发指南_使用样式表Qss自定义界面

进行本篇介绍学习前&#xff0c;请先参考链接01_1_Qt工程实践_Qt样式表Qss&#xff0c;后再结合本篇进行融合学习如何使用样式表定义界面。 文章目录 1. Qt样式表2. Qt样式表句法2.1 一般句法格式2.2 选择器 (selector)2.3 子控件&#xff08;sub-controls&#xff09;2.4 伪状…

将应用设置成系统App/获取Android设备SN号

1&#xff0c;和系统签名一致&#xff1b;&#xff08;签名设置签名文件&#xff09; 2&#xff0c;配置Manifest 至此你的App就是一个系统App了&#xff0c;可以执行一些系统App才能有的操作&#xff0c;如获取机器SN号&#xff1a; public String getSerialNumber() {Strin…