当前位置:  开发笔记 > 编程语言 > 正文

如果使用vtable实现具有虚函数的类,那么如何实现没有虚函数的类?

如何解决《如果使用vtable实现具有虚函数的类,那么如何实现没有虚函数的类?》经验,为你挑选了2个好方法。

特别是,无论如何都不会有某种功能指针?



1> Euro Micelli..:

我认为" 带有虚函数的类是用vtable实现的 "这句话会误导你.

该短语使得听起来像具有虚拟功能的类是" 以A方式 "实现的,而没有虚函数的类是" 以B方式 "实现的.

实际上,具有虚函数的类除了作为类实现之外,还具有vtable.另一种看待它的方法是"'vtable'实现类的'虚函数'部分".

有关它们如何工作的更多细节:

所有类(使用虚拟或非虚拟方法)都是结构.C++中结构和类之间的唯一区别是,默认情况下,成员在结构中是公共的,在类中是私有的.因此,我将在这里使用术语class来引用结构和类.记住,它们几乎是同义词!

数据成员

类(结构)只是连续内存块,其中每个成员按顺序存储.请注意,由于CPU体系结构原因,某些成员之间会存在间隙,因此块可能大于其各部分的总和.

方法

方法或"成员函数"是一种幻觉.实际上,没有"成员函数"这样的东西.函数始终只是存储在内存中的一系列机器代码指令.要进行呼叫,处理器会跳转到该内存位置并开始执行.你可以说所有方法和函数都是"全局的",任何相反的指示都是编译器强制执行的一种错觉.

显然,一个方法就像它属于一个特定的对象,所以很明显还有更多的事情发生.为了将方法(函数)的特定调用绑定到特定对象,每个成员方法都有一个隐藏参数,该参数是指向相关对象的指针.该成员是隐藏的,你不会自己将它添加到你的C++代码中,但没有什么神奇之处 - 它是非常真实的.当你这样说:

void CMyThingy::DoSomething(int arg);
{
    // do something
}

编译器真的这样做:

void CMyThingy_DoSomething(CMyThingy* this, int arg)
{
    /do something
}

最后,当你写这个:

myObj.doSomething(aValue);

编译器说:

CMyThingy_DoSomething(&myObj, aValue);

无需任何地方的函数指针!编译器已经知道您正在调用哪个方法,因此它直接调用它.

静态方法甚至更简单.它们没有this指针,因此它们的编写与编写它们完全相同.

那是!其余的只是方便的语法糖:编译器知道方法属于哪个类,因此它确保它不允许您在不指定哪个类的情况下调用该函数.它还使用这些知识转化myItemthis->myItem时,它的明确这样做.

(是的,这是正确的:方法中的成员访问总是通过指针间接完成,即使你没有看到一个)

(编辑:删除最后一句并单独发布,以便单独批评)



2> Richard Cord..:

非虚拟成员函数实际上只是一个语法糖,因为它们几乎像普通函数,但具有访问检查和隐式对象参数.

struct A 
{
  void foo ();
  void bar () const;
};

基本相同:

struct A 
{
};

void foo (A * this);
void bar (A const * this);

需要vtable,以便为特定的对象实例调用正确的函数.例如,如果我们有:

struct A 
{
  virtual void foo ();
};

'foo'的实现可能近似于:

void foo (A * this) {
  void (*realFoo)(A *) = lookupVtable (this->vtable, "foo");
  (realFoo)(this);   // Make the call to the most derived version of 'foo'
}

推荐阅读
手机用户2502852037
这个屌丝很懒,什么也没留下!
DevBox开发工具箱 | 专业的在线开发工具网站    京公网安备 11010802040832号  |  京ICP备19059560号-6
Copyright © 1998 - 2020 DevBox.CN. All Rights Reserved devBox.cn 开发工具箱 版权所有