C ++消歧:子对象和子类对象

时间:2013-08-26 19:34:34

标签: c++ inheritance subclass

基本上标题是什么。我一直将Base对象称为子对象。这是正确的吗subobject == superclass object也是正确的吗?哪一个更受欢迎?

subclass表示派生类,subclass object表示派生类'对象,对吧?

我的困惑是subclass object!= subobject

如果其中任何一项是正确的,无论如何..

由于

5 个答案:

答案 0 :(得分:13)

C ++标准清楚地定义了子对象是什么。也就是说,许多人在谈论C ++时并没有(精确地)使用标准语言。一个流行的例子是术语对象。对于像Java这样的语言,有些人倾向于仅在的实例意义上使用 object ,这不适用于int。在C ++标准中,int是一个对象。

标准在[intro.object] / 2中说了什么:

  

对象可以包含其他对象,称为子对象。子对象可以是成员子对象基类子对象或数组元素。不是任何其他对象的子对象的对象称为完整对象

这应该在(可能的)内存布局的上下文中理解。它没有完全指定,但很可能是这样的:

class Foo { int i; };
class Bar : public Foo { int j; };

Bar类型的对象在内存中可能如下所示:

+-Bar-------------------+
|  +-Foo-----+          |
|  |  int i  |  int j;  |
|  +---------+          |
+-----------------------+

也就是说,Foo的成员是Bar的成员,就像Bar的直接成员一样。因此Bar的每个对象都包含“Foo类型的对象。还要考虑

Bar b;
Bar* pBar = &b;
Foo* pFoo = &b;
+-Bar-------------------+
|  +-Foo-----+          |
|  |  int i  |  int j;  |
|  +---------+          |
+--^--------------------+
^  |pFoo
|pBar

要允许pFoo指向类型为Foo的完整对象和类型为Foo的子对象,需要有一个整体和(内存方面)类型为{的独立对象在Foo类型的任何对象内{1}}。在编译时可能不知道哪一个是这种情况,但为Bar生成的代码必须适用于两者。

这一切都在as-if规则下指定,即它不一定是这样,但它必须以这种方式表现出来。此外,这不是实际的内存布局,但它是一种常见的实现方式。


在[intro.object] / 4

  

如果完整对象,数据成员或数组元素属于类类型,则其类型被视为最多派生类,以区别于任何基类子对象的类类型;最派生类类型或非类类型的对象称为大多数派生对象

supersede superset 之外,标准中没有使用 super 这个词。有基类派生类(以及〜对象)。


在C ++语言标准之外,术语超类用于引用基类,术语子类用于引用到派生类。这是指OO概念和分类,就像 Species 是生物学中 Genus 的子类别。

但是在这种分类中,没有内存布局,因此无需谈论子对象。有实例对象(在OO意义上),所以你可以谈论超类的对象子类的对象。混淆可能源于将子类对象缩写为子对象,并将OO的语言与C ++标准中的语言混合。

答案 1 :(得分:4)

当一般面向对象术语与C ++相关术语混合时会发生这种情况。

  • 子对象:存储在另一个对象(数组元素,基类对象和数据成员对象)中的任何对象。
  • 子类:引用C ++中的一般对象定义术语称为“派生类”
  • 超类:一般的面向对象术语,指的是C ++中的所谓“基类”。
  • 完整对象:未存储在另一个对象中的任何对象。

只是一点提示 - 在C ++领域谈话时,我尝试使用C ++术语。在Java领域谈话时,我正在尝试使用Java术语。

答案 2 :(得分:2)

子对象是对象的C ++术语,是另一个对象的一部分;无论是成员还是基类。

子类是其他语言中使用的术语,以及对继承的更一般性讨论,表示派生类。这来自将类层次结构绘制为倒置树的常规,其根位于顶部。 C ++没有使用这个术语,可能是因为你描述的潜在混淆。

为避免在讨论C ++中的继承时出现混淆,请使用 base 派生类的标准术语。

答案 3 :(得分:0)

我认为大多数情况下,子对象容易混淆地引用子类对象的基类相关部分(例如一些vtable指针),特别是在涉及多重继承的设置中。我建议避免这个术语并坚持使用更为明确的术语(超级/次级,基础/派生)。

答案 4 :(得分:-1)

我可以称之为父对象吗?