删除的构造函数必须是私有的吗?

37
class A
{
public:
    A() = default;
    A(const A&) = delete;
};

class A
{
public:
    A() = default;

private:
    A(const A&) = delete;
};

这两个定义在任何情况下都是完全相同的吗?


12
我将我的已删除函数公开,因为这是向公众用户发出的通知,表明它无法被默认构造(在您的情况下)。 - Nawaz
2个回答

51

它们只在生成的诊断方面不同。如果将其设为private,将会报告额外且多余的访问冲突:

class A
{
public:
    A() = default;
private:
    A(const A&) = delete;
};

int main()
{
    A a;
    A a2=a;
}

以上操作会导致GCC 4.8产生以下额外的输出:

main.cpp: In function 'int main()':
main.cpp:6:5: error: 'A::A(const A&)' is private
     A(const A&) = delete;
     ^
main.cpp:12:10: error: within this context
     A a2=a;
          ^

因此,我建议始终将删除的方法设为public


7
我将我的删除函数公开,因为这是向公共用户发布通知的方式,告知它无法被默认构造(在OP的情况下)。 - Nawaz
4
没问题,@Nawaz说得对,因此它也可以被视为类的界面/文档的一部分。 - Daniel Frey

14

我想扩展Daniel Frey的答案。与其将删除的方法始终设置为public,我宁愿为这些方法分配一个访问修饰符,如果它们没有被删除,你会给这些方法的(假设)访问修饰符。(如果程序员有选择,我不喜欢始终这个词。如果确实将删除的方法设置为public是铁板钉钉的,那么语言本身应该强制执行。)

一些经验法则/指南:

  • 对于大多数情况下,具体类和抽象类的拷贝和移动赋值运算符将为public
  • 对于大多数情况下,具体类的拷贝和移动构造函数将为public
  • 对于大多数情况下,抽象类的拷贝和移动构造函数将为protected
  • 对于大多数情况下,仅能由friends实例化的具体final类的拷贝和移动构造函数将为private

在所有情况下,你需要向类的适当用户宣布而不是所有用户宣布。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接