多态类中的虚函数表是Compile-Time,还是Run-Time时发生的

来源:互联网 发布:反对本本主义 知乎 编辑:程序博客网 时间:2024/06/05 02:16

备注       sizeof这个函数也是编译时决定的,可以当常量用。

然而这一道很经典的笔试面试测验问题,批复起来也是形形色色,各有各的说法。例如,看到过相仿下面这段话的批复:

虚函数它虚就虚在所谓“迟到联编”可能“动态联编”上,一个类函数的调用并不是在编译时刻被确定的,而是在运行时刻被确定的。由于编写代码的时候并不能确定被调用的是基类的函数还是哪个派生类的函数,因而被成为“虚”函数。

看起来有理由的一段话,问题很显明。

轻微解释:

虚函数,和虚函数表是两个东西,就算虚函数究竟怎么调用时在Run-Time时确定,和虚函数表可未曾什么联系。

再来看另外一个解释:

vtable的内容是在编译时确定好的,每个Class都有一个vtable相对应。
在运行时,率先创立vtable的内存映象,然后,在创立对象时,将相应的vtable的地址写入对象的vptr。因而,这个问题本身就不是十鲜确定。比拟严密的该当这么说:vtable的内容是在编译时确定的,而内存中的vtable是在运行时创立的。

不过,这里有一个问题必需解释,编译时的vtable中并无须定是虚函数在运行时的恳挚地址,而很可能是一个offset,因为,代码和数据在运行时都会有一个重定向的过程,这个过程大局部情形是由垄断系统举行的,这时运行期vtable的内容即便编译时的映象;而有些时候,过程会对切身举行重定向调剂,这时内存中vtable的内容即便编译收获穿越计算获得的值

这个就不得了了,这里解释的不但是垄断系统有可能让vtable变成在运行时发生,而且有可能因为不同的编译器,而让这个vtalbe揭示Compile time确定,和Run-time确定两种情形。

(不知为什么,陡然我就开始思忖 这个问题究竟是为什么被提出来呢?为了验证什么而存在呢?)

在<<Inside the C++ Object Model>>这本书中,我看到了规范

How might the table containing the virtual function addresses be constructed? In C++,ys.yst1608.com the set of virtual functions capable of being invoked through an object of its class is known at compile time. Moreover, this set is invariant. It cannot be added to nor can a virtual instance be replaced at runtime. The table, therefore, serves only as a passive repository. Since neither its size nor its contents change during program execution, its construction and access can be completely handled by the compiler. No runtime intervention is necessary.

Having the address available at runtime, however, is only half the solution. The other half is finding the address.

即便这本经典书籍的经典内容定夺了答案。

批复Compile-Time发生虚构函数表,就对了!!!(看起来好像是一个二选一的推断题目一样)。

重要的是,万一不能解释虚构函数表指针是在运行期被初始化(告终多态的关键所在),那这道题目其实批复得未曾任何含义。对我们会意C++多态的性质和必需性也未曾帮助。

其实我想解释是:目前的测验和招聘工作中,对于一些知识点的核实,是否真的让应聘人员懂得了其与该工作岗位的差距,是否在工作岗位上会用到相干知识,是否对于告终其本职工作有帮助,还是必需出题者更好的举行琢磨!

对于以上***,迎接大家拍砖!

附注:

因为语言的多样性,不确定性,万一虚构函数表指针在运行期才被初始化,固然虚构函数表是在编译期后其大小和内容就被确定,然而也不能说就被发生了啊!!因而这道题目就变成了捣糨糊。良好改成 虚构函数表的大小和内容是什么时候确定的?(Compile-Time 可能Run- Time)

最后,顺带给出原题规范的答案:

虚构函数表是在编译期就发生了,各个虚构函数这时被组织成了一个虚构函数的入口地址的数组。

而对象的隐藏成员“虚构函数表指针”是在运行期,即构造函数被调用时举行初始化的,这是告终多态的关键。

原创粉丝点击