问题描述
std :: shared_ptr具有一个别名构造函数,该函数允许新创建的shared_ptr与现有的共享指针共享状态,同时指向其他对象.
std::shared_ptr has an aliasing constructor that allows newly created shared_ptr to share state with an existing shared pointer while pointing to some other object.
我当时正在考虑滥用此构造函数,以将指向全局对象的指针放置在shared_ptr中:
I was thinking about abusing this constructor to put pointer to some global object inside shared_ptr:
int global = 0;
int main()
{
// because we point to global object we do not need to track its lifetime
// so we use empty shared_ptr<void> as a provider of shared state
std::shared_ptr<int> p(std::shared_ptr<void>(), &global);
std::shared_ptr<int> pp = p;
return *pp;
}
我的问题是:合法吗?该代码可在主要编译器上成功运行.
My question is: Is it legal? The code successfully works on major compilers.
请注意,我不问这是否是一件好事.我确实知道,有一种使用无操作删除器将指向全局对象的指针放入shared_ptr中的规范方法.如果合法,这也有点令人不安,因为有可能具有可取消引用的shared_ptr,弱指针始终过期:
Note, that I do not ask if it's a good thing to do. I do understand that there's a canonical way of putting pointers to global objects into shared_ptr using no-op deleter. It is also a bit disturbing if it is legal, because it would be possible to have dereferenceable shared_ptr, weak pointers to which are always expired:
std::shared_ptr<int> p(std::shared_ptr<void>(), &global);
std::weak_ptr<int> w = p;
if (p) // p is alive and well
{ // and w is not
*w.lock(); // and here program crashes
}
推荐答案
众所周知,在当前解决方案中,p
的use_count()
为零,这就是weak_ptr
过期的原因.根据C ++草案N4296,这似乎可以:
As you already know, with your current solution, p
has a use_count()
of zero, that's why the weak_ptr
is expired. This seems to be ok, according to the C++ draft N4296:
20.8.2.2.2 shared_ptr析构函数[util.smartptr.shared.dest]
〜shared_ptr();
1种效果:
(1.1)— 如果*此为空或与另一个shared_ptr实例(use_count()> 1)共享所有权, 没有副作用.
(1.2)—否则,如果*这拥有一个对象p和一个删除器d,则调用d(p).
(1.3)—否则,*这拥有一个指针p,而删除p称为
20.8.2.2.2 shared_ptr destructor [util.smartptr.shared.dest]
~shared_ptr();
1 Effects:
(1.1) — If *this is empty or shares ownership with another shared_ptr instance (use_count() > 1), there are no side effects.
(1.2) — Otherwise, if *this owns an object p and a deleter d, d(p) is called.
(1.3) — Otherwise, *this owns a pointer p, and delete p is called
强调我的.
您可以使用以下代码代替,该代码给出shared_ptr
且use_count()
为1:
emphasis mine.
You could use the following instead which gives a shared_ptr
with a use_count()
of one:
std::shared_ptr<int> p(&global, [](int*){});
这使用一个空的自定义删除器.
This uses an empty custom deleter.
这篇关于使用C ++共享指针的别名构造函数和空的共享指针的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!