【发布时间】:2013-02-10 22:29:25
【问题描述】:
我有一个继承自 enable_shared_from_this 的类。它对子对象有shared_ptrs,并且有一个“根”对象,因此整个层次结构由shared_ptr 管理。这样一个对象可以有多个父对象并且可以安全地销毁。
我开始编写一个构造函数,然后我意识到用户应该使用std::shared_ptr 来管理对象,就像我在内部所做的那样,就像我在一些现有的库中看到的那样,例如 gtkmm。所以我可以做我看到其他人做的事情:隐藏构造函数,并编写一个静态成员函数 create(),它返回一个 shared_ptr 给新对象。显然 create() 非常有用,因为没有它我需要调用 std::make_shared() 或稍后调用 std::shared_from_this()。
但是我应该隐藏构造函数,为什么?我可以猜到一些很好的理由,例如它强制用户使用 shared_ptr,否则对象会被删除,因此可以保证用户不使用不受 shared_ptr 管理的“孤立”对象。它确保用户不会忘记手动创建 shared_ptr,因为忘记意味着对象被删除,即使它被复制(深拷贝,而不是指针的副本),然后用户很快就会注意到。
另一个有趣的选择是不使用 create() 静态方法,而是使用 add_child() 方法作为创建新对象的唯一方法。这保证了它链接到层次结构。问题:灵活性。如果有人想单独使用一个对象,那是不可能的,除非你派生类。
你会/我应该怎么做?隐藏/不隐藏ctor? add_child()? create()?
【问题讨论】:
-
你似乎很清楚地了解了利弊。如果类需要由
shared_ptr管理,我会隐藏构造函数。 -
@DrewDormann 在我的用例中,所有对象都在层次结构中,但总的来说,我不知道。唯一的判断方法是共享内存和对象的经验,而我没有。像 gtkmm 这样的库隐藏了 ctor - 等等,我想我明白了!隐藏 ctor 有一个很好的理由:防止用户在共享对象上意外调用 delete。对于隐藏的 ctor,只有在显式调用 shared_ptr::get() 时才会发生 :)
-
但还有一个问题:将 create() 设为公开还是将用户限制为 add_child()?
-
@fr33domlover 如果你想阻止用户删除,你隐藏析构函数,而不是构造函数。 (然后您必须在创建时将其传递给 shared_ptr,这会迫使您提供一个函数来创建所述指针)。
-
“然后你必须在创建时将 [dtor] 传递给 shared_ptr”......他说你可以将“删除”函数传递给
shared_ptr构造函数。 en.cppreference.com/w/cpp/memory/shared_ptr/shared_ptr
标签: c++ c++11 constructor shared-ptr