gpt4 book ai didi

c++ - 当 shared_ptr 的实例仍在范围内时共享指针的对象被删除

转载 作者:太空狗 更新时间:2023-10-29 19:46:37 26 4
gpt4 key购买 nike

我有一个 STL 映射,其中包含指向在多个线程中操作的对象的共享指针。 shared_ptr 拥有的对象正在被删除,而智能指针仍然存在于容器和/或其他函数的范围内。所有 shared_ptr 实例都是按值传递的(因此它不是滥用引用的问题)。我对这个来源印象深刻here只要 shared_ptr 的实例存在(从现有的 shared_ptr 复制而来),它拥有的对象就不会被释放。

这基本上是我正在做的:

/* Remove Event response in Thread A */
std::map<std::string, std::shared_ptr<object>>::iterator it = objects.find(id);
if(it != objects.end())
{
std::shared_ptr<object> ob = it->second;
objects.erase(it);

//Do cleanup work with ob
}

/* Add Event response in Thread B */
std::map<std::string, std::shared_ptr<object>>::iterator it = objects.find(id);
if(it == objects.end())
{
std::shared_ptr<object> ob(new object(id));
objects[id] = ob;

//Do setup work with ob
}

/* Duty Cycle Event response in Thread C (very frequent) */
//Take snapshot of objects so Remove Event does not invalidate iterators of duty cycle
std::map<std::string, std::shared_ptr<object>> temp_objects = objects;
for(std::map<std::string, std::shared_ptr<object>>::const_iterator it = temp_objects.begin(); it != temp_objects.end(); ++it)
{
std::shared_ptr<object> ob = it->second;
//Access violation can (but doesn't always) occur when dereferencing ob (ob is empty)
}

我做错了什么?我是在滥用共享指针还是对它们的运行方式做出了不正确的假设?

最佳答案

shared_ptr 对象的引用计数是原子的;这是 C++11 所要求的。但是,不需要的是 std::map 操作 是原子的。他们当然不是。

不能保证您可以从一个线程插入并从另一个线程删除,并且仍然保持 map 内容的完整性。因此,除非您放入自己的互斥体或一些其他同步,以防止 map 本身出现竞争条件,否则您的代码将会中断。

这与shared_ptr无关;那只是问题的症状。这是关于包含它们的 map

关于c++ - 当 shared_ptr 的实例仍在范围内时共享指针的对象被删除,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/9147258/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com