Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How do I implement virtual methods in implementation files?

Tags:

c++

C++ noob question:

lets say I want to use an abstract class with multiple methods as an interface:

// this is AbstractBase.hpp

class AbstractBase
{
public:
  virtual int foo() = 0;
  virtual int bar() = 0;
  // imagine several more pure virtual methods are here
};

I want a subclass implementing all the virtual methods, and I don't want to implement them in the header file, but in their implementation files instead.

Do I really have to declare all these methods again in the subclass declarations like this? I'm thinking there should be a way to avoid this step (coming from ObjC, Java)

// this is Concrete.hpp

class Concrete : public AbstractBase
{
public:
  int foo();
  int bar();
  // need to copy paste all the method declarations here again...? why?
};

what I would like to do is implement the methods in the implementation file like this:

// this is Concrete.cpp

#include "Concrete.hpp"

int Concrete::foo()
{
    return 666;
}

// etc...

but can't figure out how, without re-declaring the interface in each subclass.

like image 230
spinalwrap Avatar asked Jan 01 '16 15:01

spinalwrap


2 Answers

Although you can avoid writing function header signature for the second time if you combine the definition with the declaration "Java-style", i.e.

class Concrete : public AbstractBase
{
public:
  int foo() override {return 666;}
};

C++ does not let you avoid the declaration step when you want to provide your definition separately.

The reason for this is that the declaration is primary, while definitions are secondary. In order to be able to write

int Concrete::foo()
{
    return 666;
}

in your CPP file you need to tell the compiler that Concrete has an intention to override foo in its header.

like image 78
Sergey Kalinichenko Avatar answered Sep 30 '22 20:09

Sergey Kalinichenko


If you like an abstrct base class you have to make your methods pur virtual (only declaration without implementation (write =0behind the declaration of your method):

class AbstractBase
{
public:
  virtual int foo() = 0; // <- = 0 
  virtual int bar() = 0; // <- = 0
};

Use the override keyword, so you will get an compile error if decalaration of mehtod changes in base class:

Concrete.hpp

class Concrete : public AbstractBase
{
public:
  int foo() override; // <- override
  int bar() override; // <- override
};

Finaly implement your methods like you did it in your question:

Concrete.cpp

#include "Concrete.hpp"

int Conrete::foo()
{
    return 666;
}

int Conrete::bar()
{
    return 777;
}

But you have to declare all those methods from base class in subclass which are abstract.

like image 43
Rabbid76 Avatar answered Sep 30 '22 18:09

Rabbid76