【C++11多线程】线程的创建、结束、传递参数

news2024/11/17 17:28:40

文章目录

  • 1.普通函数作为线程函数
    • 1.1 thread
    • 1.2 join()
    • 1.3 detach()
    • 1.4 joinable()
  • 2.函数对象作为线程函数
  • 3.lambda表达式作为线程函数
  • 4.类成员函数作为线程函数
  • 5.向线程函数传递参数

1.普通函数作为线程函数

程序运行起来,生成一个进程,其中主线程从 main() 函数开始执行,当主线程从 main() 函数返回,则整个进程执行完毕。也就是说,整个进程是否执行完毕的标志是主线程是否执行完毕。

既然主线程从 main() 函数开始执行,那么我们自己创建的线程也需要从一个函数开始运行,一旦这个函数运行完毕,我们自己创建的线程也结束运行。

1.1 thread

头文件 #include <thread>

thread 是一个类,thread td(myThread) 是利用构造函数创建了一个 thread 类对象 td,传入参数 myThread 是一个可调用对象。

C++ 中的可调用对象可以是函数、函数指针、lambda表达式、bind创建的对象或者重载了函数调用运算符的类对象。

1.2 join()

join() 是 thread 类中的一个方法,其作用是:阻塞主线程,让主线程等待子线程执行完毕,然后子线程和主线程汇合,然后主线程再往下执行。

#include <iostream>
#include <thread>
using namespace std;

// 线程入口函数
void myThread()
{
	cout << "myThread begin" << endl;
	cout << "myThread running1" << endl;
	cout << "myThread running2" << endl;
	cout << "myThread running3" << endl;
	cout << "myThread running4" << endl;
	cout << "myThread running5" << endl;
	cout << "myThread running6" << endl;
	cout << "myThread end" << endl;
	return;
}

int main()
{
	thread td(myThread); // 创建了线程,线程入口函数是myThread(),myThread线程开始执行

	td.join(); // 阻塞主线程并等待myThread子线程执行完,当子线程执行完毕,这个join()函数就执行完毕,主线程继续往下执行

	cout << "hello world1" << endl;
	cout << "hello world2" << endl;
	cout << "hello world3" << endl;
	cout << "hello world4" << endl;
	cout << "hello world5" << endl;
	cout << "hello world6" << endl;

	return 0;
}

输出结果如下:

在这里插入图片描述

1.3 detach()

detach() 是 thread 类中的一个方法,其作用是:一旦 detach() 之后,与主线程关联的 thread 对象就会失去与主线程的关联,此时这个子线程就会驻留在后台运行(守护线程),这个子线程就相当于被 C++ 运行时库接管了,当这个子线程执行完成后,由运行时库负责清理该线程的相关资源。

一旦调用了 detach(),就不能再用 join() 了,否则系统会报异常。

#include <iostream>
#include <thread>
using namespace std;

// 线程入口函数
void myThread()
{
	cout << "myThread begin" << endl;
	cout << "myThread running1" << endl;
	cout << "myThread running2" << endl;
	cout << "myThread running3" << endl;
	cout << "myThread running4" << endl;
	cout << "myThread running5" << endl;
	cout << "myThread running6" << endl;
	cout << "myThread end" << endl;
	return;
}

int main()
{
	thread td(myThread); // 创建了线程,线程入口函数是myThread(),myThread线程开始执行

	td.detach(); // 主线程可以不等子线程结束就先结束,子线程不会被强制结束,而是可以继续运行,驻留在后台,由C++运行时库接管

	cout << "hello world1" << endl;
	cout << "hello world2" << endl;
	cout << "hello world3" << endl;
	cout << "hello world4" << endl;
	cout << "hello world5" << endl;
	cout << "hello world6" << endl;

	return 0;
}

输出结果如下:

在这里插入图片描述

1.4 joinable()

joinable() 是 thread 类中的一个方法,其作用是:判断线程是否可以成功使用 join() 或 detach()。

  • 如果返回 true,表示可以调用 join() 或 detach();
  • 如果返回 false,表示已经调用过 join() 或 detach(),不能再调用 join() 或 detach() 了。

2.函数对象作为线程函数

#include <iostream>
#include <thread>
using namespace std;

class A
{
public:
	int m_i;

	A(int i) : m_i(i)
	{
		cout << "构造函数执行,this = " << this << endl;
	}
	
	A(const A& a) : m_i(a.m_i)
	{
		cout << "拷贝构造函数执行,this = " << this << endl;
	}

	~A()
	{
		cout << "析构函数执行,this = " << this << endl;
	}
	
	// 线程入口函数
	void operator()(int num)
	{
		cout << "m_i = " << m_i << ",num = " << num << ",this = " << this << endl;
	}
};

int main()
{
	int i = 100;
	A a(i);

	thread td(a, 18);
	td.join();

	cout << "hello world1" << endl;
	cout << "hello world2" << endl;
	cout << "hello world3" << endl;

	return 0;
}

输出结果如下:

在这里插入图片描述

3.lambda表达式作为线程函数

#include <iostream>
#include <thread>
using namespace std;

int main()
{
    // 线程入口函数
	auto myThread = [] {
		cout << "myThread begin" << endl;
		cout << "myThread running1" << endl;
		cout << "myThread running2" << endl;
		cout << "myThread running3" << endl;
		cout << "myThread running4" << endl;
		cout << "myThread running5" << endl;
		cout << "myThread running6" << endl;
		cout << "myThread end" << endl;
	};

	thread td(myThread);
	td.join();

	cout << "hello world1" << endl;
	cout << "hello world2" << endl;
	cout << "hello world3" << endl;

	return 0;
}

输出结果如下:

在这里插入图片描述

4.类成员函数作为线程函数

#include <iostream>
#include <thread>
using namespace std;

class A
{
public:
	int m_i;
	
	A(int i) : m_i(i)
	{
		cout << "构造函数执行,this = " << this << endl;
	}
	
	A(const A& a) : m_i(a.m_i)
	{
		cout << "拷贝构造函数执行,this = " << this << endl;
	}

	~A()
	{
		cout << "析构函数执行,this = " << this << endl;
	}

	// 线程入口函数
	void work(int num)
	{
		cout << "m_i = " << m_i << ",num = " << num << ",this = " << this << endl;
	}
};

int main()
{
	A a(100);

	thread td(&A::work, a, 18);
	td.join();

	return 0;
}

输出结果如下:

在这里插入图片描述

5.向线程函数传递参数

关于向线程函数传递参数的具体细节,可以看下这篇文章:https://www.cnblogs.com/chen-cs/p/13056703.html

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

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

毕业设计 基于单片机的地震探测器系统 - stm32 物联网 嵌入式

文章目录0 前言1 简介2 主要器件3 实现效果4 硬件设计3轴加速度计ADXL335ADXL335加速度计的工作原理电路图和连接5 部分核心代码最后0 前言 &#x1f525; 这两年开始毕业设计和毕业答辩的要求和难度不断提升&#xff0c;传统的毕设题目缺少创新和亮点&#xff0c;往往达不到毕…

[附源码]计算机毕业设计基于Springboot物品捎带系统

项目运行 环境配置&#xff1a; Jdk1.8 Tomcat7.0 Mysql HBuilderX&#xff08;Webstorm也行&#xff09; Eclispe&#xff08;IntelliJ IDEA,Eclispe,MyEclispe,Sts都支持&#xff09;。 项目技术&#xff1a; SSM mybatis Maven Vue 等等组成&#xff0c;B/S模式 M…

拳头游戏教程

文章目录一、初谈游戏美术游戏美术师的作用视觉效果二、概念创造1.项目前期准备2.生成创意3.获取反馈三、角色设计从概念到3D模型3D建模的过程表面改变解剖学协作改变四、环境设计什么是环境美术创建的过程视觉层次可信度效率五、技术美术骨骼制作定制化工具移植开发流程shader…

模拟百度网盘

linux下基于多线程和tcp去实现了一个模拟网盘,实现cs之间的下载互传大文件,实现断点续传,秒传,利用md5进行校验,实时显示百分比 整体框架: 整个项目是在Linux环境下用C语言开发的,基于TCP协议,采用多线程的socket通信方式。 普通上传和秒传:客户端会先计算文件的MD…

(六)Vue之MVVC

文章目录MVVCVue中的MVVCVue代码中的MVVMVue学习目录 上一篇&#xff1a;&#xff08;五&#xff09;Vue之data与el的两种写法 MVVC MVVM是Model-View-ViewModel的简写。它本质上就是MVC 的改进版。 MVC参考&#xff1a;MVC架构模式 MVVM 就是将其中的View 的状态和行为抽象…

YOLOv5实现车辆检测(含车辆检测数据集+训练代码)

YOLOv5实现车辆检测(含车辆检测数据集训练代码) 目录 YOLOv5实现车辆检测(含车辆检测数据集训练代码) 1. 前言 2. 车辆检测数据集说明 &#xff08;1&#xff09;车辆检测数据集 &#xff08;2&#xff09;自定义数据集 3. 基于YOLOv5的车辆检测模型训练 &#xff08;1…

【Python】-- Turtle绘图(使用代码画喜欢的图形!)

什么是Turtle&#xff1f; turtle库是Python语言中一个很流行的绘制图像的函数库&#xff0c;可以想象一个小乌龟在爬行&#xff0c;它的爬行轨迹就是绘制出来的图形&#xff0c;在一个横轴为x、纵轴为y的坐标系原点&#xff0c;(0,0)位置开始&#xff0c;它根据一组函数指令的…

罐头食品市场向好,APS车间排产软件保证食品制造企业有序生产

这些年&#xff0c;随着人们健康意识的不断提升&#xff0c;一些消费者认为&#xff0c;罐头的保质期长是因为添加了大量的防腐剂&#xff0c;但实际上这是一种错误的认知。罐头食品不需要添加防腐剂&#xff0c;而是采用热力杀菌和密封工艺&#xff0c;达到商业无菌和真空保存…

如何管好一个迭代?让数据帮你回答这些关键问题

对软件从业者来说&#xff0c;『敏捷开发』早已不是一个新名词。 相比瀑布模型&#xff0c;敏捷开发模型更强调演进式开发&#xff0c;快速灵活地应对变化&#xff0c;最终交付使客户满意的产品。这就要求研发团队内部、研发团队与产品乃至与业务、客户之间的密切沟通。当变化…

CW6163C车床的三维仿真及加工工艺

目录 1 传动轴分析 - 1 - 1.1 传动轴结构特点 - 1 - 1.2 传动轴的工艺分析 - 1 - 1.3 传动轴的技术要求 - 2 - 2 毛坯的选择 - 3 - 2.1 毛坯的类型 - 3 - 2.2 毛坯余量的确定 - 3 - 2.3 毛坯草图 - 4 - 3 工艺规程设计 - 5 - 3.1 定位基准的选择 - 5 - 3.1.1 粗基准的选择 - 5 …

div做一个简单的自适应布局

div做一个简单的自适应布局 效果 代码&#xff1a; <template><div class"main-page"><div></div><div></div><div></div><div></div><div></div></div> <style lang"le…

深入浅出——spring和AspectJ实现AOP操作

基本概念可看我之前的文章 AOP——基本概念、底层原理&#xff0c;这次直接来实现AOP的操作&#xff0c;在介绍操作之前&#xff0c;我们得先介绍AOP的各种术语 aop操作术语 1、连接点&#xff08;JoinPoint&#xff09;&#xff1a; 类里面哪些方法可以被增强&#xff0c;这…

小白必知必会的几个IP地址知识

小白必知必会的几个IP地址知识1.IP地址的定义2.IP地址的组成3.IP地址的分类4.广播地址5.IP多播6.子网掩码7.CIDR8.全局地址和私有地址1.IP地址的定义 IP地址(IPv4地址)由32位正整数来表示。TCP/IP通信要求将这样的IP地址分配给每一个参与通信的主机。IP地址在计算机内部以二进…

三问HPE,你真的想买下Nu­t­a­n­ix么?

【全球存储观察 | 热点关注】据多个媒体消息报道&#xff0c;慧与科技HPE在近几个月与超融合提供商Nutanix就收购进行了谈判。 在这之前的2017年2月&#xff0c;HPE以6.5亿美元收购了超融合全球老二SimpliVity&#xff0c;后来整合成了HPE重要的超融合产品线&#xff0c;并进一…

全栈测试工程师是怎么样练成的?

不久前&#xff0c;一位朋友让帮忙推荐个测试工程师&#xff0c;于是聊到了他们对测试工程师的诉求。 朋友公司是一家做教育软件的公司&#xff1a;Web端、App端产品都有涉及。 最初的诉求就是想找一位有1-2年相关产品测试经验的人即可。 但经过几轮沟通后&#xff0c;他的诉求…

.NET代码调优让程序占用内存减少

建了一个默认的ASP.NET Core Web API的项目,也就是那个WeatherForecast的默认项目模板,然后他把默认的生成5条数据的代码,改成了生成150000条数据,其他代码没变,如下: public IEnumerable<WeatherForecast> Get(){return Enumerable.Range(1, 150000).Select(index…

毕业设计-基于机器学习的二维码和条形码识别

目录 前言 课题背景和意义 实现技术思路 实现效果图样例 前言 &#x1f4c5;大四是整个大学期间最忙碌的时光,一边要忙着备考或实习为毕业后面临的就业升学做准备,一边要为毕业设计耗费大量精力。近几年各个学校要求的毕设项目越来越难,有不少课题是研究生级别难度的,对本科…

ssrf漏洞--补充部分

可以使用的协议 下面是攻击时常用的协议 http/httpsftptftpsftpfiledictGopherldapldapsldapi file://path/to/file dict://<user>;<auth><host>:<port>/d:<word>:<database>:<n> dict://127.0.0.1:1337/stats ftp://127.0.0.1/ …

git常见bug及其解决方案

git常用命令和常见bug1、git主要命令2、git commit 提交的时候报错husky > pre-commit hook failed3、git命令行将本地仓库代码上传到github或gitlab远程仓库4、没有git pull更新代码就push的报错5、git 拉取某个分支的某一个commit的代码6、GitLab中配置SSH key7、配置成和…

QT:布局管理器消息盒子

让组件在水平和垂直方向对齐 有三种常用布局管理器&#xff1a; 水平&#xff0c;QHBoxLayout 垂直&#xff0c;QVBoxLayout 网格&#xff0c;QGridLayout(使布局好的界面嵌套到主窗口) 1.让组件大小固定 修改属性&#xff1a;minimusize&#xff0c;maxmumsize 最小和最大组件…