说说shared_ptr“线程安全性,原理”
创始人
2024-06-02 01:38:25
0

在多线程的编译环境中,调用不同shared_ptr实例的成员函数是不需要额外的同步手段的,即使这些shared_ptr拥有的是同样的对象。

但是如果多线程“访问(有写操作)”同一个shared_ptr,则需要同步,否则就会有race condition发生。也可以使用shared_ptr overloads of atomic functions来防止race condition的发生。

多个线程同时同一个shared_ptr对象是线程安全的,但是,如果是多个线程对同一个shared_ptr对象进行读和写,则需要加锁。

多线程读写shared_ptr所指向的同一个对象,
不管是相同的shared_ptr对象,还是不同的shared_ptr对象,都需要加锁保护。

eg:

shared_ptrglobal_instance=make_shared(0);
std::mutex g_i_mutex;void thread_fcn() 
{
//std::lock_guardlock(g_i_mutex);
//shared_ptrlocal=global_instance;    for(int i=0; i<100000000; i++)    {        *global_instance = *global_instance + 1;        //*local=*local+1;    }
}
void main() {    thread thread1(thread_fcn);    thread thread2(thread_fcn);                thread1.join();    thread2.join();      cout<<"*global_instance is"<<*global_instance;
}

在线程函数thread_fcn的for循环中,2个线程同时对global_instance进行加1的操作。这就是典型的非线程安全的场景,最后的结果是未定的,
运行结果为:*global_instance is197240539;

如果使用的是每个线程的局部shared_ptr对象local,因为这些local指向相同的对象,因此结果也是未定的,
运行结果为:*global_instance is160285803;

因此,这种情况下必须加锁,将thread_fcn中的第一行代码的注释去掉之后,不管是使用global_instance,还是使用local,
得到的结果都是:*global_instance is 200000000

#include 
#include 
using namespace std;int main()
{shared_ptr sp1(new int(100));cout << "当前计数: " << sp1.use_count() << endl;//1auto sp2 = sp1;cout << "当前计数: " << sp1.use_count() << endl;//2{auto sp3 = sp2;cout << "当前计数: " << sp1.use_count() << endl;//3}cout << "当前计数: " << sp1.use_count() << endl;//2return 0;
}

相关内容

热门资讯

监控摄像头接入GB28181平... 流程简介将监控摄像头的视频在网站和APP中直播,要解决的几个问题是:1&...
Windows10添加群晖磁盘... 在使用群晖NAS时,我们需要通过本地映射的方式把NAS映射成本地的一块磁盘使用。 通过...
protocol buffer... 目录 目录 什么是protocol buffer 1.protobuf 1.1安装  1.2使用...
在Word、WPS中插入AxM... 引言 我最近需要写一些文章,在排版时发现AxMath插入的公式竟然会导致行间距异常&#...
【PdgCntEditor】解... 一、问题背景 大部分的图书对应的PDF,目录中的页码并非PDF中直接索引的页码...
修复 爱普生 EPSON L4... L4151 L4153 L4156 L4158 L4163 L4165 L4166 L4168 L4...
Fluent中创建监测点 1 概述某些仿真问题,需要创建监测点,用于获取空间定点的数据࿰...
educoder数据结构与算法...                                                   ...
MySQL下载和安装(Wind... 前言:刚换了一台电脑,里面所有东西都需要重新配置,习惯了所...
MFC文件操作  MFC提供了一个文件操作的基类CFile,这个类提供了一个没有缓存的二进制格式的磁盘...