gpt4 book ai didi

c++ - 为什么即使不涉及虚函数,虚继承也需要虚表?

转载 作者:可可西里 更新时间:2023-11-01 17:15:33 24 4
gpt4 key购买 nike

我读了这个问题:C++ Virtual class inheritance object size issue ,并且想知道为什么虚拟继承会导致类中有一个额外的 vtable 指针。

我在这里找到了一篇文章:https://en.wikipedia.org/wiki/Virtual_inheritance

这告诉我们:

However this offset can in the general case only be known at runtime,...

我在这里不明白什么是运行时相关的。完整的类继承层次结构在编译时是已知的。我了解虚函数和基指针的使用,但虚拟继承没有这样的东西。

有人可以解释为什么一些编译器 (Clang/GCC) 使用 vtable 实现虚拟继承,以及它在运行时中是如何使用的吗?

顺便说一句,我也看到了这个问题:vtable in case of virtual inheritance , 但它只指向与虚函数相关的答案,这不是我的问题。

最佳答案

The complete class inheritance hierarchy is already known in compile time.

没错;因此,如果编译器知道最派生对象的类型,那么它就知道该对象中每个子对象的偏移量。为此,不需要 vtable。

例如,如果 BC两者实际上都源自 A , 和 D派生自 BC , 然后在下面的代码中:

D d;
A* a = &d;

来自 D* 的转换至 A*最多就是给地址加一个静态偏移量。

但是,现在考虑这种情况:

A* f(B* b) { return b; }
A* g(C* c) { return c; }

在这里,f必须能够接受指向任何 B 的指针对象,包括 B可能是 D 的子对象的对象对象或其他一些最派生的类对象。编译时f ,编译器不知道 B 的完整派生类集.

如果B object 是最派生的对象,然后是 A子对象将位于某个偏移量处。但是如果B怎么办?对象是 D 的一部分目的? D对象只包含一个 A对象,并且它不能位于其通常与 两者 B 的偏移处和 C子对象。所以编译器必须为 A 选择一个位置D 的子对象,然后它必须提供一种机制,以便某些带有 B* 的代码或 C*可以找出A在哪里子对象是。这完全取决于最派生类型的继承层次结构——因此 vptr/vtable 是一种合适的机制。

关于c++ - 为什么即使不涉及虚函数,虚继承也需要虚表?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/57482925/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com