You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

C++中针对虚基类的static_cast是否会触发运行时vptr查询?

问题

假设有如下代码:

struct Granny {
  int g;
};
struct Mom : virtual Granny {
  int m;
};
struct Son : Mom {
  int s;
};

int main() {
  int x;
  std::cin >> x;
  Mom* mom = (x ? new Son : new Mom);
  Granny* granny = static_cast<Granny*>(mom);
}

这些类并非多态类(Granny没有虚函数),但根据x的取值,mom指针指向的对象内存布局会有所不同:Granny子对象相对于对象起始地址的偏移量为16字节或12字节。

问题:此处的static_cast是否不会执行“简单指针移位”,而是编译为“解引用mom对象的vptr(虚表指针),通过索引查找虚偏移量,最终按该偏移量调整指针”的逻辑?即static_cast会增加两个额外的运行时操作吗?如果不是,请解释实际发生的行为。

解答

是的,这里的static_cast不会是编译期固定的指针移位,而是会触发运行时的虚表查询操作,具体逻辑和你描述的一致:

  1. 解引用mom指针指向对象的vptr,获取对应的虚表地址;
  2. 从虚表的特定位置读取Granny子对象相对于当前对象起始地址的偏移量;
  3. 用该偏移量调整mom指针,得到最终的Granny*指针。

之所以需要运行时操作,核心原因是虚拟继承的特性:当类使用虚拟继承时,虚拟基类子对象的偏移量不是固定的——它取决于实际创建的对象类型(这里可能是Mom或Son)。编译期无法预知x的取值,也就无法确定mom实际指向的对象类型,自然没法硬编码一个固定的偏移量。

另外要注意:哪怕Granny本身没有虚函数,只要类(Mom)使用了虚拟继承,编译器就会在Mom和Son的对象中插入vptr,这个vptr的作用之一就是存储虚拟基类的偏移信息,用于这种跨类型的指针转换。

内容的提问来源于stack exchange,提问作者gh_shark

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.20 12:12:13