Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Constructor got deleted by compiler when I have a virtual method?

Tags:

c++

I came across a situation that can be summarized in the following code snippet. Basically, I would like my classes to inherit constructors. It works, but compilation fails as soon as I have a virtual method defined in C. Apparently the compiler deleted the constructor.

My questions are:

  1. Why does the compiler do that?
  2. I can work around by defining constructors in B and C and delegate eventually to A's constructor. Is there a better way to do this?
#include <iostream>

struct A {
  A() = delete;
  A(int x) : x_(x) {}
  int x_;
};

struct B : public A {
};

struct C : public B {
  // What? defining virtual method kills the inherited constructor
  //virtual void foo() {}
};

int main() {
  C c{10};
  std::cout << "Hello World: " << c.x_ << std::endl;
}
like image 874
fatdragon Avatar asked Apr 23 '21 00:04

fatdragon


People also ask

Can we use virtual function in constructor?

You can call a virtual function in a constructor, but be careful. It may not do what you expect. In a constructor, the virtual call mechanism is disabled because overriding from derived classes hasn't yet happened. Objects are constructed from the base up, “base before derived”.

Can we call virtual function in constructor in Java?

As a general rule, you should never call virtual functions in constructors or destructors. If you do, those calls will never go to a more derived class than the currently executing constructor or destructor. In other words, during construction and destruction, virtual functions aren't virtual.

Can a pure virtual function be called using an object?

Virtual Function in C++When you refer to a derived class object using a pointer or a reference to the base class, you can call a virtual function for that object and execute the derived class's version of the function.

What does pure virtual function call mean?

A pure virtual function is a function that must be overridden in a derived class and need not be defined. A virtual function is declared to be “pure” using the curious =0 syntax. For example: class Base {


1 Answers

Constructors are inherited only when you explicitly declare the inherited constructors. This is done as follows:

struct B : public A {
    using A::A;
};

struct C : public B {
    using B::B;
};

In your program, you are not using inherited constructors; you are using aggregate initialization. Adding a virtual function makes C no longer an aggregate, so aggregate initialization cannot be used. If you declare inherited constructors, then you can construct C without having to use aggregate initialization.

like image 192
Brian Bi Avatar answered Sep 28 '22 15:09

Brian Bi