简体   繁体   English

虚函数在构造函数中的奇怪行为

[英]Strange behavior of virtual functions in constructor

I have searched related questions about virtual functions in constructors and I know that if we call virtual functions in constructor in base class, only the base version of virtual is invoked. 我已经搜索了有关构造函数中的虚函数的相关问题,并且我知道,如果我们在基类中的构造函数中调用虚函数,则仅会调用virtual的基础版本。

However, what I post below shows that the calling of virtual in Base constructor actually calls the virtual version in D2. 但是,我在下面发布的内容表明在Base构造函数中对virtual的调用实际上在D2中调用了虚拟版本。

I know it may seems kind of duplicated, but I wonder if anyone help me with it. 我知道它似乎有些重复,但我想知道是否有人帮助我。

My Code: 我的代码:

#include<iostream>
struct B
{
  B()=default;
  B(const B& b)  {b.fun();}
  virtual void fun()const  {std::cout<<"virtual_B"<<std::endl;}
};
struct D1:public B
{
  D1()=default;
  D1(const D1& d1):B(d1)  {}
  void fun()const  {std::cout<<"virtual_D1"<<std::endl;}
};
struct D2:public D1
{
  D2()=default;
  D2(const D2& d2):D1(d2)  {}
  void fun()const  {std::cout<<"virtual_D2"<<std::endl;}
};
int main()
{
  D2 a;
  D2 b=a;
  return 0;
}

Because you call b.fun() , b is existing fully constructed object. 因为您调用b.fun() ,所以b是现有的完全构造的对象。 Virtual methods don't work in virtual fashion if you call them on the this pointer which is not yet fully constructed object. 如果在尚未完全构造的对象this指针上调用虚拟方法,则虚拟方法将无法以虚拟方式工作。 If you call other objects' virtual method on constructor they will totally work as expected. 如果在构造函数上调用其他对象的虚拟方法,它们将完全按预期工作。

I know that if we call virtual functions in constructor in base class, only the base version of virtual is invoked. 我知道,如果我们在基类的构造函数中调用虚拟函数,则仅会调用虚拟的基本版本。

You have misunderstood that rule. 您误解了该规则。

It does not mean any way of calling the virtual function from within the constructor. 这并不意味着从构造函数内部调用虚拟函数的任何方式。 It mean calling the virtual function for the object being constructed. 这意味着为正在构造的对象调用虚函数。

Within the constructor, you called the virtual function for a different (and fully constructed) object whose compile time class was B and runtime class was D2. 在构造函数中,您为另一个(完全构建的)对象调用了虚拟函数,该对象的编译时间类为B,运行时类为D2。 On that object you get the D2 version of the virtual function. 在该对象上,您将获得虚拟功能的D2版本。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM