60人参与 • 2026-07-24 • C/C++
虚函数表的初始化分为两个阶段,一个是编译/链接期,一个是运行期,二者分工不同:
编写包含虚函数的类(比如 class a { virtual void f(); })并编译时:
a::f 的地址)。每个包含虚函数的对象,都会有一个隐藏的 vptr 成员(指向所属类的 vtable),这个指针的初始化:
vptr 在对象构造函数执行的最开始阶段完成初始化(早于构造函数的函数体执行)
vptr,再初始化子类自己的 vptr。vptr 在程序启动后的全局初始化阶段(main 函数执行前)完成。vptr 在 operator new 分配内存后、构造函数执行前初始化。#include <iostream>
using namespace std;
class base {
public:
base() {
// 此时 vptr 已经指向 base 的 vtable,调用虚函数会走 base 版本
func(); // 输出 "base::func"
}
virtual void func() { cout << "base::func" << endl; }
};
class derived : public base {
public:
derived() {
// 此时 vptr 已经切换到 derived 的 vtable
func(); // 输出 "derived::func"
}
void func() override { cout << "derived::func" << endl; }
};
int main() {
derived d;
// 构造过程:
// 1. 初始化 base 部分 → vptr 指向 base::vtable → 调用 base::func
// 2. 初始化 derived 部分 → vptr 切换到 derived::vtable → 调用 derived::func
return 0;
}
输出结果:
base::func
derived::func
即vptr 在构造函数执行时已经完成初始化,且子类构造时会覆盖父类的 vptr。
vptr 都指向这份 vtable。vptr 初始化在构造函数的“初始化列表阶段”(编译器自动插入),早于函数体执行。vptr 指向它。vptr。到此这篇关于c++中虚函数表的初始化时机的文章就介绍到这了,更多相关c++虚函数表初始化内容请搜索代码网以前的文章或继续浏览下面的相关文章希望大家以后多多支持代码网!
您想发表意见!!点此发布评论
版权声明:本文内容由互联网用户贡献,该文观点仅代表作者本人。本站仅提供信息存储服务,不拥有所有权,不承担相关法律责任。 如发现本站有涉嫌抄袭侵权/违法违规的内容, 请发送邮件至 2386932994@qq.com 举报,一经查实将立刻删除。
发表评论