C++虚函数除了vtable怎么实现? [复制]
Posted
技术标签:
【中文标题】C++虚函数除了vtable怎么实现? [复制]【英文标题】:How can C++ virtual functions be implemented except vtable? [duplicate] 【发布时间】:2011-07-22 00:42:16 【问题描述】:可能重复:A question about virtual mechanism in C++
在 C++ 中使用 vtable 是实现虚成员函数机制的唯一方法吗?还有哪些其他方式?
【问题讨论】:
可能会构建一些可行的奇怪机制(基于嵌入式类型 id 和函数 id 或其他东西的全局跳转表) - 但从未听说过其他实际可行的实现。 你是说内部?如果是,那么,这是最快的方法。您将需要一个用于快速调度的数组,并且您将存储指针。所以你最终会得到像 vtable 这样的东西。 @sharptooth:与***.com/questions/4352032/…重复 @Als:我在询问之前搜索并没有找到那个。 @sharptooth:可能有太多带有相似标签的问题。我能找到它只是因为我是前一阵子问这个问题的人。 :) 【参考方案1】:我不知道有任何编译器在不使用 vtable 方法的情况下实现虚函数。
然而,理论上,可以创建一个对象指针和指向虚函数的指针表的内部映射,类似于map<objPtr, functionTable*>
,通过以下方式实现动态多态性虚函数。但这会使动态调度比 vtable-approach 慢。
似乎 vtable-approach 可能是实现动态多态性的最快机制。也许,这就是所有编译器都采用这种方法的原因!
【讨论】:
【参考方案2】:从技术上讲,动态分派所需要的只是能够识别对象的动态类型,给定一个指向它的指针。因此,任何类型的隐藏(或不那么隐藏)typeid 字段都可以工作。
动态调度将使用该 typeid 来查找关联的函数。该关联可以是一个 hastable 或一个 typeid 为索引的数组,或任何其他合适的关系。 vptr 恰好是用最少的步骤实现这一目标的方法。
【讨论】:
【参考方案3】:另一种可能的实现是将指向虚函数的指针直接存储到对象中。当然,这个解决方案从未在实践中使用过(至少在我所知道的任何语言中),因为它会导致内存占用量的急剧增加。然而,有趣的是,使用此实现的代码实际上可以运行得更快,因为它通过抑制对 vptr 的需求来移除间接层。
【讨论】:
【参考方案4】:另一个已知的机制是类型分派函数。实际上,您将 vtable 指针替换为 typeid(小枚举)。 (动态)链接器收集给定虚函数的所有覆盖,并将它们包装在 typeid 字段上的一个大 switch 语句中。
理论上的理由是,这用大量可预测的跳跃代替了间接跳跃(不可预测的)。在选择枚举值方面有一些技巧,switch 语句也可以相当有效(即比 lineair 更好)
【讨论】:
以上是关于C++虚函数除了vtable怎么实现? [复制]的主要内容,如果未能解决你的问题,请参考以下文章