请看样品,
std::atomic < std::shared_ptr < int > > a;
std::shared_ptr < int > b;
std::shared_ptr < int > c = std::make_shared < int > (10);
while(a.compare_exchange_weak(b, c));
assert(a.load() == c);
assert(a.load().use_count() == 2); // <- assertion is failed.
你怎么看?是编译器错误吗?
在win32模式下使用msvs 2013构建
答案 0 :(得分:7)
您的程序显示未定义的行为。
29.5 / 1 有一个通用的类模板
atomic<T>
。模板参数T
的类型应该是可复制的(3.9)。
shared_ptr<int>
并非易于复制。
答案 1 :(得分:4)
根据Igor的回答,std::atomic<std::shared_ptr<T>>
没有定义的行为。您需要使用the non-member shared_ptr
atomic function overloads,详见C ++11§20.7.2.5shared_ptr
原子访问[util.smartptr.shared.atomic]。
std::shared_ptr < int > a;
std::shared_ptr < int > b;
std::shared_ptr < int > c = std::make_shared < int > (10);
while(std::atomic_compare_exchange_weak(&a, &b, c))
;
assert(std::atomic_load(&a) == c);
assert(std::atomic_load(&a).use_count() == 2);
对我来说,标准并没有强制要求template <typename T> struct std::atomic<shared_ptr<T>>
部分专业化以实现这些功能,这似乎很奇怪。
我没有看到Microsoft's documentation of the <memory>
header中的非成员原子重载,因此它们可能无法在VS2013中实现。
答案 2 :(得分:0)
问题是关于C ++ 11的,但值得指出的是,自C ++ 20 以来,OP代码是有效的,因为{{1 }}和std::atomic
。
请参阅:std::atomic<std::shared_ptr<T>>
at cppreference
另外,使用shared_ptr
的替代方法是deprecated in C++20。