基本上标题是什么。我一直将Base对象称为子对象。这是正确的吗subobject
== superclass object
也是正确的吗?哪一个更受欢迎?
subclass
表示派生类,subclass object
表示派生类'对象,对吧?
我的困惑是subclass object
!= subobject
。
如果其中任何一项是正确的,无论如何..
由于
答案 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 ++术语。在Java领域谈话时,我正在尝试使用Java术语。
答案 2 :(得分:2)
子对象是对象的C ++术语,是另一个对象的一部分;无论是成员还是基类。
子类是其他语言中使用的术语,以及对继承的更一般性讨论,表示派生类。这来自将类层次结构绘制为倒置树的常规,其根位于顶部。 C ++没有使用这个术语,可能是因为你描述的潜在混淆。
为避免在讨论C ++中的继承时出现混淆,请使用 base 和派生类的标准术语。
答案 3 :(得分:0)
我认为大多数情况下,子对象容易混淆地引用子类对象的基类相关部分(例如一些vtable指针),特别是在涉及多重继承的设置中。我建议避免这个术语并坚持使用更为明确的术语(超级/次级,基础/派生)。
答案 4 :(得分:-1)
我可以称之为父对象吗?