首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >接口vtable

接口vtable
EN

Stack Overflow用户
提问于 2012-06-26 03:51:14
回答 3查看 3.6K关注 0票数 15

接口(只有纯虚函数的多态类)有vtable吗?由于接口本身并不实现多态函数,也不能直接构造,因此链接器不需要放置vtable。是真地吗?我特别关注MSVC编译器。

EN

回答 3

Stack Overflow用户

回答已采纳

发布于 2012-06-26 04:01:18

是的,它们确实如此。这其中有很多很好的理由。

第一个很好的原因是,即使是纯虚方法也有实现。隐式或显式。实现一个调用纯虚函数的技巧是相对容易的,所以你基本上可以为你的一个函数提供一个定义,调用它,看看会发生什么。出于这个原因,首先应该有一个虚拟表。

将虚表放入基类还有另一个原因,即使它的所有方法都是纯虚的,并且没有其他数据成员。当使用多态性时,指向基类的指针在整个程序中传递。为了调用虚方法,编译器/运行时应该计算出虚表相对于基指针的相对偏移量。如果C++没有多重继承,可以假设抽象基类的偏移量为零(例如),在这种情况下,那里可能没有vtable (但由于#1的原因,我们仍然需要它)。但是因为涉及到多重继承,所以"vtable在那里的偏移量为0“的技巧不会起作用,因为根据基类的数量(和类型),可能会有两到三个vtable。

可能还有其他我还没有想到的原因。

希望能有所帮助。

票数 8
EN

Stack Overflow用户

发布于 2012-06-26 03:55:17

从纯C++的角度来看,这是一个学术问题。虚函数不一定要用vtable实现,如果是这样,就没有可移植的方法来获取它们。

如果您特别关心MSVC编译器,那么您可能希望使用__declspec(novtable)来装饰您的接口。

(通常,在常见的实现中,抽象类可能需要vtable,例如:

代码语言:javascript
复制
struct Base {
    Base();
    virtual void f() {}
    virtual void g() = 0;
};

void h(Base& b) {
    b.f(); // Call f on a Base that is not (yet) a Derived
           // vtable for Base required
}

Base::Base() {
    h(*this);
}

struct Derived : Base {
    void g() {}
};

int main() {
    Derived d;
}

)

票数 5
EN

Stack Overflow用户

发布于 2012-06-26 16:20:32

vtable不是必需的,但很少会优化出来。MSVC提供了__declspec(novtable)扩展,它显式地告诉编译器可以删除vtable。如果没有这样做,编译器将不得不检查自己是否没有使用vtable。这并不是特别困难,但仍然远非微不足道。而且由于它在常规代码中没有提供真正的速度优势,所以我所知道的任何编译器都没有实现该检查。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/11196329

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档