C++ 受保护继承的实际用途是什么?

C++ 受保护继承的实际用途是什么?,c++,inheritance,protected,C++,Inheritance,Protected,公共继承很容易 答:公共B表示每个A都是B。在大多数编程语言中,如vb.net和objective-c,这是唯一的继承类型 私有继承也很容易,但毫无意义 答:私有B意味着A是由B实现的。然而,这是没有意义的,因为这意味着A应该包含B。所有权意味着更少的耦合,没有缺点 然后我们保护了遗产 谁能给我解释一下这到底是干什么的?有人说这是一种“作为一种关系”。我还不是很清楚 有没有人有过这样的例子:人们以良好的方式(和良知)使用受保护的遗产进行实际的生产性使用?受保护的遗产的主要动机是正交性。 在所有其

公共继承很容易

答:公共B表示每个A都是B。在大多数编程语言中,如vb.net和objective-c,这是唯一的继承类型

私有继承也很容易,但毫无意义

答:私有B意味着A是由B实现的。然而,这是没有意义的,因为这意味着A应该包含B。所有权意味着更少的耦合,没有缺点

然后我们保护了遗产

谁能给我解释一下这到底是干什么的?有人说这是一种“作为一种关系”。我还不是很清楚


有没有人有过这样的例子:人们以良好的方式(和良知)使用受保护的遗产进行实际的生产性使用?

受保护的遗产的主要动机是正交性。 在所有其他上下文中,您有三种不同的访问控制: 私人的、受保护的和公共的。为什么要继承遗产 不同?在实践中,人们可以说没有必要 或一般用于受保护的访问。这可能言过其实了 情况确实如此,但可以肯定的是,受到保护的远远少于 私人的或公共的

而且,私有继承并非毫无意义,事实上, 对应于继承的原始用法。一旦 执行实现的基类使用虚拟函数 派生类必须重载,不能使用包含

私有继承也很容易,但毫无意义

答:私有B意味着A是由B实现的。然而,这是没有意义的,因为这意味着A应该包含B。所有权意味着更少的耦合,没有缺点

您可能看不到私有继承的原因,但这并不意味着它毫无意义。 有好几种情况下,私人继承有其原因。乍一看,您是对的,私有继承意味着有一种类似于聚合的关系,并且私有继承有一种(稍微)更紧密的耦合

支持私人继承而非侵害的原因可能有以下几种:

  • 通过私有继承,您也可以继承typedef。在某些情况下(例如traits类),私有继承只是在基类中重新定义大量typedef的替代方法
  • 在很少情况下,您必须在“真实”(即公共)基类之前初始化成员。实现这一点的唯一方法是使该成员成为在公共基类之前继承的私有基类
  • 有时,您需要访问成员的受保护成员。如果不能更改成员类本身,则必须使用私有继承来访问它们
  • 如果一个成员没有自己的数据成员,它仍然会占用空间。使其成为私有基类可以实现空基类优化,从而减小类对象的大小
  • 更多信息,请参见下面詹姆斯的评论
这些原因显然是技术原因,有些人甚至会说“黑客”。然而,这样的原因是存在的,所以私有继承并非完全没有意义。它不是“纯OO风格”——但是C++也不是纯OO语言。 一旦您了解了私有继承的原因,受保护继承的原因就非常简单:


如果您有理由私下继承某些内容,并且希望使派生类可以访问这些好处(即,您的类或typedefs的潜在成员),请使用受保护的继承。显然,私有继承应该很少使用,继承保护更大。

可能是错误的,但我想我读了一本金C++的书(不记得哪一本),即<代码>保护< /COD>继承几乎是(几乎)无稽之谈,而且几乎从来没有使用过。例如“保留供将来使用”。但是,我可能会再次撒谎:)作者Johannes Schaub实际上发现了一个用例。它仍然称之为“很少有用”。或者尝试和私有继承也几乎没有用,因为它应该是所有权。@JimThio,除非所有权不起作用。(mixin将是一个很好的例子。)更一般地说,当您想要公开基类接口的一部分(但不是全部)时,私有继承也是一个实用的解决方案<代码>使用比转发函数要简单得多。值得指出的是,在SimultTalk中,原始继承相对于私有继承更接近于C++中的公共。继承最初设计用于支持共享实现,而不是共享接口。当然,您忽略了私有继承最常见的原因:基类使用模板方法模式提供了可定制的实现,而且你必须覆盖它的虚拟功能。更不用说,有时候,你实现一个特定接口的事实是你的客户端的一个实现细节。GUI小部件是GUI事件监听器这一事实只涉及小部件本身(以及它注册事件的位置)。@JamesKanze感谢您的补充。我担心,如今支持共享实现并不是继承的好理由,因为人们往往被“一切都必须是纯OO”的思维毒害。关于“纯OO”:如上所述,在这个术语的发明者(也是Smalltalk的作者之一)的心目中,继承只是实现的继承。第一种使用OO标签的语言使用duck类型,因此不需要继承接口。(参见今天的Python,了解其工作原理的示例。)我曾经使用受保护的虚拟基来管理链接器各个过程的命令行参数;每个过程都由它自己的类型处理,链接器类型是从每个过程类型私有派生的。事后看来,我不确定这是一个好的设计还是只是炫耀。