C++多线程编程:其一、thread类概述

news/2024/7/24 4:29:37 标签: c++

thread是C++11版本中出现的线程对象,可以让程序员非常方便地创建线程。
非空的thread对象创建以后,线程就会自动运行起来。简单地理解,一个线程对象中会传入一个函数指针,之后编译器会构造一个栈,将这个函数指针压栈。函数就可以视为任务,从而实现了任务并发。

一、如何创建线程对象:

(1)空thread对象:

thread t;

如果后面没有对其赋值的话,这就是一个毫无意义的操作。

(2)使用全局函数创建thread对象:

void f(){
    cout<<"I love coding"<<endl;
}
int main()
{
    thread t(f);
    t.join();
}

全局函数也可以带参数

void f(int a){
    cout<<"I love coding"<<endl;
    cout<<a;
}
int main()
{
    thread t(f,1);
    t.join();
}

(3)使用静态成员函数创建thread对象:

class A{
public:
    static void f();
};

void A::f(){
    cout<<"I love coding"<<endl;
}
int main()
{
    thread t(A::f);
    t.join();
}

因为静态函数是类公有的,所以只需要标注类名即可。

(4)使用非静态成员函数创建thread对象:

class A{
public:
    void f();
};

void A::f(){
    cout<<"I love coding"<<endl;
}
int main()
{
    A a;
    thread t(&A::f,&a);
    t.join();
}

首先需要将对象构造出来,然后将对象的this指针作为入参。

二、线程持有的资源

网上有各种各样的多线程教程,老生常谈的一句话是“线程持有的资源如何如何”。那么thread到底持有的是什么资源?
本人才疏学浅,操作系统学的实在是不咋地,深入理解不太行。但是这个资源,可以简单看作一个结构体:

_Thrd_t _Thr; //其实_Thrd_t 是类型的别名
 
typedef _Thrd_imp_t _Thrd_t;    // 而_Thrd_imp_t是一个结构体
 
typedef struct {	/* 线程 标识符 */
    void *_Hnd;	    /* 操作系统句柄 */
    unsigned int _Id;    // 线程id
} _Thrd_imp_t;

thread持有的资源,可以看作是一个线程id+一个操作系统句柄。后面会说明,这两个资源,每个thread对象都是不一样的。

所以,thread对象,只能移动构造,不能拷贝构造。只能移动赋值,不能拷贝赋值。

void f(){
}
int main()
{
    thread t1(f);
    cout<<"t1 id : "<<t1.get_id()<<endl<<endl;

    thread t2(move(t1));
    cout<<"t1 id : "<<t1.get_id()<<endl;
    cout<<"t2 id : "<<t2.get_id()<<endl;

    t2.join();
}

输出:

t1 id : 2

t1 id : thread::id of a non-executing thread
t2 id : 2

可见,移动构造之后,t1持有的资源全部给了t2.
假如有一种场景,f()正在执行,发生了资源移动,有问题吗?
没有任何问题。因为线程实际上是操作系统持有的资源,当thread对象创建好以后,线程怎么跑起来和thread对象基本没关系了,thread对象里面不过是保存了一个句柄,句柄就是指向操作系统内核的指针。资源移动无非是将指针转移给了其他的thread对象。

但是,thread保留了这个句柄,说明对象就有了这个线程的所有权,可以阻塞它、分离它,或者进行其他操作。


http://www.niftyadmin.cn/n/5154520.html

相关文章

c面向对象编码风格(上)

面向对象和面向过程的基本概念 面向对象和面向过程是两种不同的编程范式&#xff0c;它们在软件开发中用于组织和设计代码的方式。 面向过程编程&#xff08;Procedural Programming&#xff09;是一种以过程&#xff08;函数、方法&#xff09;为核心的编程方式。在面向过程…

【iOS】——知乎日报第三周总结

文章目录 一、获取新闻额外信息二、工具栏按钮的布局三、评论区文字高度四、评论区长评论和短评论的数目显示五、评论区的cell布局问题和评论消息的判断 一、获取新闻额外信息 新闻额外信息的URL需要通过当前新闻的id来获取&#xff0c;所以我将所有的新闻放到一个数组中&…

SQL 左连接 LEFT JOIN 关键字||SQL右连接 RIGHT JOIN 关键字

SQL 左连接 LEFT JOIN 关键字 SQL左链接LEFT JOIN关键字返回左表&#xff08;表1&#xff09;中的所有行&#xff0c;即使在右表&#xff08;表2&#xff09;中没有匹配。如果在正确的表中没有匹配&#xff0c;结果是NULL。 SQL LEFT JOIN 语法 SELECT column_name(s) …

[100天算法】-搜索旋转排序数组(day 60)

题目描述 升序排列的整数数组 nums 在预先未知的某个点上进行了旋转&#xff08;例如&#xff0c; [0,1,2,4,5,6,7] 经旋转后可能变为 [4,5,6,7,0,1,2] &#xff09;。请你在数组中搜索 target &#xff0c;如果数组中存在这个目标值&#xff0c;则返回它的索引&#xff0c;否…

linux 驱动——字符设备驱动(自动生成设备节点文件)

文章目录 字符设备驱动字符设备 APP生成 dev 节点的原理配置内核自动创建设备节点模块使用 字符设备驱动 #include "linux/device/class.h" #include "linux/export.h" #include "linux/uaccess.h" #include <linux/types.h> #include &l…

JavaEE平台技术——Spring和Spring Boot

JavaEE平台技术——Spring和Spring Boot 1. 控制反转1.1. IoC是什么1.2. IoC能做什么1.3. IoC和DI 2. SpringBean对象定义3. Spring容器4. SpringBoot 在观看这个之前&#xff0c;大家请查阅前序内容。 &#x1f600;JavaEE的渊源 &#x1f600;&#x1f600;JavaEE平台技术——…

[题] 改革春风吹满地 #图论 #多边形面积

题目 HDU 2036 改革春风吹满地 题解 参考博客&#xff1a;HDU 2036 改革春风吹满地 代码 #include<bits/stdc.h> using namespace std; const int N 110; //叉乘计算面积的公式&#xff0c;以(0,0)为起始点划分 int main() {int n;while(~scanf("%d", &…

asp.net人事管理信息系统VS开发sqlserver数据库web结构c#编程Microsoft Visual Studio

一、源码特点 asp.net 人事管理信息系统是一套完善的web设计管理系统&#xff0c;系统具有完整的源代码和数据库&#xff0c;系统主要采用B/S模式开发。开发环境为vs2010&#xff0c;数据库为sqlserver2008&#xff0c;使用c#语言 开发 asp.net 人事管理系统1 应用技术…