C++关于vtable的奇怪错误

今天遇到了一个关于C++ vtable的奇怪错误,乍一看还真的很难理解,值得记录一下。

假设下面的程序:

class Father {

public:

  virtual void function() const = 0;

};

class Child : public Father {

public:

Child(unsigned int data)

   : data(data) {}

  void function() const;

  //data

private:

  int data;

};

int main() {

  Child m_child(3);

  return 0;

}

看起来这段程序没有任何问题。尽管Child类中的function()没有定义,但是在main()中并不会用到Child::function(),所以一般情况下编译和连接都没有问题。

但是实际情况是:编译会通过,连接时会报出类似如下的错误:

undefined reference to `vtable for Child

感觉上有函数没有定义,可是找不到任何需要定义的函数。这里的错误很可能报在构造函数的位置,使得错误信息更难理解了。信息中的vtable是唯一有用的信息,提示错误和虚函数有关。

为了能正确连接,这段程序中我们必须定义一个function()的函数体。由于function是Father中纯虚函数的一个重载,Child类则默认存在一个虚函数表以存储重载虚函数。但由于function()没有函数定义,编译生成的目标代码没有生成任何有效的虚函数表,因而导致连接时出现找不到vtable的错误。如果function()是一个普通函数则不会出现如上问题。

感觉上,如果一个子类重载了任何虚函数,需要提供至少一个虚函数的实现,否则就会出现如上很难理解的错误。

Advertisements

关于 W. Song
Research Associate in the University of Cambridge

发表评论

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / 更改 )

Twitter picture

You are commenting using your Twitter account. Log Out / 更改 )

Facebook photo

You are commenting using your Facebook account. Log Out / 更改 )

Google+ photo

You are commenting using your Google+ account. Log Out / 更改 )

Connecting to %s

%d 博主赞过: