Loading...

Initializing abstract class with deleted copy constructor


I have an abstract class with deleted copy constructor and copy assignment operator that is meant to be used as a public interface:

struct connection {
    // Make object non copyable.
    connection(const connection &) = delete;
    auto operator=(const connection &) -> connection & = delete;
    // Make class abstract.
    virtual ~connection() = 0;
  };

I'm trying to create a class that inherits from it:

struct abstract_connection : connection {...};

but I get the following error in the constructor:

constructor for 'abstract_connection' must explicitly initialize the base class 'connection' which does not have a default constructor

Why does this happen when I delete the copy constructor and operator?

- - Source

Answers

answered 1 week ago Holt #1

According to the standard:

[class.default.ctor#1]

[...] If there is no user-declared constructor for class X, a non-explicit constructor having no parameters is implicitly declared as defaulted ([dcl.fct.def]). [..]

Since you have user-declared the copy-constructor by deleting it, you need to user-provide the default constructor:

struct connection {

    connection(const connection &) = delete;
    auto operator=(const connection &) -> connection & = delete;
    virtual ~connection() = 0;

protected: // You likely want to make it protected.
    connection() = default;
};

answered 1 week ago Loc Tran #2

You defined the copy constructor as yourself (=delete). So Compiler saw that and it doesn't generate the default constructor. So in this case, when define new class abstract_connection that inherited from the base class connection, compiler doesn't know how to do constructor for new derived class abstract_connection. So It reported that error.

answered 1 week ago Constantinos Glynos #3

The rules behind the automatic generation of special member functions are clearly explained in Effective Modern C++ by Scott Meyers, Item 17, p.109.

In a nutshell, whenever you redefine/override a constructor, then you need to define all the needed constructors. Since you have deleted the copy constructor, you need to define the default constructor of the base class. This is becaue you are using the default constructor when you define your derived class.

This code struct abstract_connection : connection {...}; (without any given information) means that you are most likely to initialise the abstract_connection using the default ctor from connection. But the default ctor from connection is not defined.

Furthermore, you need to define your dtor, even thought it is a virtual function. The code below compiles and runs here.

struct connection
{
    connection() = default;
    connection(const connection &) = delete;

    auto operator=(const connection &) -> connection & = delete;

    virtual ~connection() = 0;
};

connection::~connection()
{}

struct abstract_connection : connection
{
    abstract_connection() : connection()
    {}

    ~abstract_connection() = default;
};

int main()
{
    abstract_connection foo;
}

comments powered by Disqus