关于shared_ptr引用计数块

tan*_*ngy 2 c++ multithreading lock-free shared-ptr c++11

我有两个关于std::shared_ptr控制块的问题:

(1)关于大小:我如何以编程方式找到控制块的确切大小std::shared_ptr

(2)关于逻辑:另外,boost::shared_ptr提到它们在控制块的变化方面是完全无锁的.(从Boost版本1.33.0开始,shared_ptr在大多数常见平台上使用无锁实现.)我没有想一想std::shared_ptr- 是否计划用于任何未来的C++版本?这不也意味着boost::shared_ptr多线程案例更好吗?

Yak*_*ont 5

控制块未暴露.在实现中,我已经读过它在大小上是动态的,以连续地存储删除器(和/或在共享的情况下,对象本身).

通常它包含至少3个指针大小的字段 - 弱,强计数和删除调用程序.

至少有一个实现依赖于RTTI; 别人不这样做.

计数操作在我读过的实现中使用原子操作; 请注意,C++不要求所有原子操作都是无锁的(我相信没有指针大小的无锁操作的平台可以是一个符合C++的平台).

它们的状态是彼此和自身一致的,但没有试图使它们与对象状态一致.这就是为什么在写pImpls上使用原始共享ptrs作为副本在某些平台上可能容易出错的原因.


Dav*_*rtz 5

(1)关于大小:我如何以编程方式找到std :: shared_ptr的控制块的确切大小?

没有办法.它无法直接访问.

(2)关于逻辑:另外,boost :: shared_ptr提到它们对于控制块的更改完全没有锁定.(从Boost版本1.33.0开始,shared_ptr在大多数常见平台上使用无锁实现. )我不认为std :: shared_ptr遵循相同的原则 - 这计划用于任何未来的C++版本吗?这不也意味着boost :: shared_ptr对于多线程案例更好吗?

绝对不.无锁实现并不总是比使用锁的实现更好.有一个额外的约束,充其量不会使实现更糟,但它不可能使实现更好.

考虑两个同样称职的程序员,每个程序员都尽力实施shared_ptr.必须产生无锁实现.另一个完全可以自由地使用他们的最佳判断.没有办法,必须产生无锁实现的那个可以在所有其他条件相同的情况下产生更好的实现.充其量,无锁实现是最好的,他们都会产生一个.更糟糕的是,在这个平台上,无锁实现具有很大的缺点,一个实现者必须使用一个.呸.

  • C++ 11只需要无锁的`std :: atomic_flag`,这足以构建一个锁,但不足以进行无锁引用计数.在标准中放置一个无锁的`std :: shared_ptr`要求/保证理论上会限制哪些平台可以支持符合C++ 11的实现.我认为这就是原因,而不是锁定在可以无锁的普通平台上实际上更好. (3认同)
  • @NicolBolas是的 这可能只是一个关于实施者认为最好的说法.很难想象你将如何在任何现代平台上需要或想要锁定 - 没有任何线程需要等待任何其他线程的情况. (2认同)