Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/134.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 删除副本&;复制分配-公共、私有还是受保护?_C++_C++11_Access Modifiers_Deleted Functions - Fatal编程技术网

C++ 删除副本&;复制分配-公共、私有还是受保护?

C++ 删除副本&;复制分配-公共、私有还是受保护?,c++,c++11,access-modifiers,deleted-functions,C++,C++11,Access Modifiers,Deleted Functions,为了使对象不可复制,我们可以显式删除其复制构造函数和复制赋值运算符 我的问题是:在课程的public、private或protected部分,什么是正确的位置?和-这个选择有什么区别吗?访问deleted函数是不相关的。事实上,对于类成员来说,添加额外的访问说明符(delete:)更有意义。我怀疑他们没有这样做的原因是,它对非成员函数不起作用 对于复制构造函数之类的东西,将其放在public部分在风格上更有意义。类没有复制构造函数这一事实是了解类接口的一个非常重要的事实 对于将特定重载声明为已删

为了使对象不可复制,我们可以显式删除其复制构造函数和复制赋值运算符


我的问题是:在课程的
public
private
protected
部分,什么是正确的位置?和-这个选择有什么区别吗?

访问
delete
d函数是不相关的。事实上,对于类成员来说,添加额外的访问说明符(
delete:
)更有意义。我怀疑他们没有这样做的原因是,它对非成员函数不起作用

对于复制构造函数之类的东西,将其放在
public
部分在风格上更有意义。类没有复制构造函数这一事实是了解类接口的一个非常重要的事实


对于将特定重载声明为已删除以便在编译器时间检测到错误的内部函数,将该函数声明为与所有其他重载相同的部分是有意义的。

delete
private
访问同样有效

如果通过重载解析选择功能,
delete
的作用是导致错误

private
的作用是,如果通过类外或其朋友的重载解析选择函数,则会导致错误

如果两个错误都适用,最终结果是相同的,但是
public
可能有助于避免编译器关于访问权限的消息,这可能会导致混淆

我们把删除的定义放在哪里有什么区别吗

从纯语言的角度来看,它绝对没有任何区别。名称查找和重载解析发生在访问检查之前。试图在重载解析结束时引用已删除的函数会导致程序格式错误,句号。编译器可能会也可能不会发出关于可访问性的另一个诊断,但程序已经有一个必须报告的错误

因此,您可以将删除的定义与所需的任何可访问性放在一起。我认为大多数人会将其保密,以符合使类不可复制的“旧”实践(将这些成员的声明放在类的私有部分,而不是定义它们),哪怕只是为了帮助那些知道旧方法的人更快地“获得它”。如果你愿意的话,这是一种混合的习语

如果需要同时支持C++03和C++11模式,那么标记为private也是不可避免的。在宏的帮助下,可以轻松使标题符合这两个标准:

#if __cplusplus >= 201103L
  #define DELETED_DEFINITION = delete
#else
  #define DELETED_DEFINITION
#endif

class noncopyable {
private:
  // This header can be compiled as both C++11 and C++03
  noncopyable(noncopyable const&) DELETED_DEFINITION;
  void operator=(noncopyable const&) DELETED_DEFINITION;
};
在班级的公共、私人或受保护区域,什么是正确的地点

我会把它们放在
公共
部分

这是因为删除构造函数或赋值运算符与使它们成为私有的/
受保护的
正交;如果不删除它们,默认情况下它们是公共的。在我看来,将删除内容放在这两个部分中的一个部分似乎暗示“如果我没有删除它们,我会将它们设置为私有/受保护的”——这不是您想要在您的案例中传达的信息


注意,编译器不关心删除Scott Meyers的哪一部分,

< P> >有效的现代C++(项目10),似乎最好是<强>定义为公共< /强>:

按照惯例,被删除的函数被声明为公共函数,而不是私有函数。 这是有原因的。当客户端代码尝试使用成员时 函数,C++在删除状态之前检查可访问性。当客户 一些编译器抱怨说,代码试图使用已删除的私有函数 仅关于函数是私有的,即使函数是 可访问性并不真正影响它是否可以被使用。值得 在修改旧代码以替换旧代码时,请记住这一点 具有已删除成员函数的私有和未定义成员函数,因为 公开新函数通常会导致更好的错误 信息


此外,我认为删除的副本构造函数/赋值应该是类接口的一部分,以便与所有类用户共享。这类信息不应通过保密来保密

函数_name()=删除对于C++11来说是新的。如果你想支持C++98/03,你就不能使用它。如果你扔掉你的旧鞋子,你会考虑把它们放在哪里吗?@Klaus:不会,但你会考虑把它们扔到哪里……建议将删除的函数公开。看见同样,叮叮当当的提迪也提出了这一点。正是这一点。在那一天,我们将这些东西保密,专门禁止人们访问它们,但这始终是一种黑客行为,只是因为我们不能
删除它们。这种考虑已不再起作用。我不记得“复制构造函数是私有的”诊断是否倾向于优先于“复制构造函数被删除”诊断(我对此表示怀疑)但是,即使它不改变访问级别,由于您给出的原因,也不是正确的做法。@LightnessRacesinOrbit我知道,我看到一些编译器在函数是私有的和被删除的情况下都会给出这两个错误。关于私密访问的问题只会成为额外的噪音。@aschepler Fair执行gcc 7.4,但不是gcc 8.1:(所以我想他们改进了)。@aschepler:Hmm。。。你在那里切换了输出标签,所以看起来7.4做了正确的事情。无论如何,谢谢。如果你想要向后兼容,那么这是必须的。@LightnessRacesinOrbit如果你想要向后兼容,你永远不应该使用C++11功能。对于删除的函数,解决方法由StoryTeller提出。但是,当使用lambdas、stl、并发等时,什么是向后兼容性解决方案?@hsalimi使用C只能做到这一点