12.6 — Pure virtual functions, abstract base classes, and interface classes

Pure virtual (abstract) functions and abstract base classes

So far, all of the virtual functions we have written have a body (a definition). However, C++ allows you to create a special kind of virtual function called a pure virtual function (or abstract function) that has no body at all! A pure virtual function simply acts as a placeholder that is meant to be redefined by derived classes.

To create a pure virtual function, rather than define a body for the function, we simply assign the function the value 0.

When we add a pure virtual function to our class, we are effectively saying, “it is up to the derived classes to implement this function”.

Using a pure virtual function has two main consequences: First, any class with one or more pure virtual functions becomes an abstract base class, which means that it can not be instantiated! Consider what would happen if we could create an instance of Base:

Because there’s no definition for getValue(), what would base.getValue() resolve to?

Second, any derived class must define a body for this function, or that derived class will be considered an abstract base class as well.

A pure virtual function example

Let’s take a look at an example of a pure virtual function in action. In a previous lesson, we wrote a simple Animal base class and derived a Cat and a Dog class from it. Here’s the code as we left it:

We’ve prevented people from allocating objects of type Animal by making the constructor protected. However, there are two problems with this:
1) The constructor is still accessible from within derived classes, making it possible to instantiate an Animal object.
2) It is still possible to create derived classes that do not redefine function speak().

For example:

This will print:

Betsy says ???

What happened? We forgot to redefine function speak(), so cow.Speak() resolved to Animal.speak(), which isn’t what we wanted.

A better solution to this problem is to use a pure virtual function:

There are a couple of things to note here. First, speak() is now a pure virtual function. This means Animal is now an abstract base class, and can not be instantiated. Consequently, we do not need to make the constructor protected any longer (though it doesn’t hurt). Second, because our Cow class was derived from Animal, but we did not define Cow::speak(), Cow is also an abstract base class. Now when we try to compile this code:

The compiler will give us a warning because Cow is an abstract base class and we can not create instances of abstract base classes:

C:\Test.cpp(141) : error C2259: 'Cow' : cannot instantiate abstract class due to following members:
        C:Test.cpp(128) : see declaration of 'Cow'
C:\Test.cpp(141) : warning C4259: 'const char *__thiscall Animal::speak(void)' : pure virtual function was not defined

This tells us that we will only be able to instantiate Cow if Cow provides a body for speak().

Let’s go ahead and do that:

Now this program will compile and print:

Betsy says Moo

A pure virtual function is useful when we have a function that we want to put in the base class, but only the derived classes know what it should return. A pure virtual function makes it so the base class can not be instantiated, and the derived classes are forced to define these functions before they can be instantiated. This helps ensure the derived classes do not forget to redefine functions that the base class was expecting them to.

Pure virtual functions with bodies

It turns out that we can define pure virtual functions that have bodies:

In this case, speak() is still considered a pure virtual function (even though it has been given a body, because of the “= 0”) and Animal is still considered an abstract base class (and thus can’t be instantiated). Any class that inherits from Animal needs to provide its own definition for speak() or it will also be considered an abstract base class.

When providing a body for a pure virtual function, the body must be provided separately (not inline).

For Visual Studio users

Visual Studio mistakenly allows pure virtual function declarations to be definitions, for example

This is wrong and cannot be disabled.

This paradigm can be useful when you want your base class to provide a default implementation for a function, but still force any derived classes to provide their own implementation. However, if the derived class is happy with the default implementation provided by the base class, it can simply call the base class implementation directly. For example:

The above code prints:

Sally says buzz

This capability isn’t used very commonly.

Interface classes

An interface class is a class that has no member variables, and where all of the functions are pure virtual! In other words, the class is purely a definition, and has no actual implementation. Interfaces are useful when you want to define the functionality that derived classes must implement, but leave the details of how the derived class implements that functionality entirely up to the derived class.

Interface classes are often named beginning with an I. Here’s a sample interface class:

Any class inheriting from IErrorLog must provide implementations for all three functions in order to be instantiated. You could derive a class named FileErrorLog, where openLog() opens a file on disk, closeLog() closes the file, and writeError() writes the message to the file. You could derive another class called ScreenErrorLog, where openLog() and closeLog() do nothing, and writeError() prints the message in a pop-up message box on the screen.

Now, let’s say you need to write some code that uses an error log. If you write your code so it includes FileErrorLog or ScreenErrorLog directly, then you’re effectively stuck using that kind of error log (at least without recoding your program). For example, the following function effectively forces callers of mySqrt() to use a FileErrorLog, which may or may not be what they want.

A much better way to implement this function is to use IErrorLog instead:

Now the caller can pass in any class that conforms to the IErrorLog interface. If they want the error to go to a file, they can pass in an instance of FileErrorLog. If they want it to go to the screen, they can pass in an instance of ScreenErrorLog. Or if they want to do something you haven’t even thought of, such as sending an email to someone when there’s an error, they can derive a new class from IErrorLog (e.g. EmailErrorLog) and use an instance of that! By using IErrorLog, your function becomes more independent and flexible.

Don’t forget to include a virtual destructor for your interface classes, so that the proper derived destructor will be called if a pointer to the interface is deleted.

Interface classes have become extremely popular because they are easy to use, easy to extend, and easy to maintain. In fact, some modern languages, such as Java and C#, have added an “interface” keyword that allows programmers to directly define an interface class without having to explicitly mark all of the member functions as abstract. Furthermore, although Java (prior to version 8) and C# will not let you use multiple inheritance on normal classes, they will let you multiple inherit as many interfaces as you like. Because interfaces have no data and no function bodies, they avoid a lot of the traditional problems with multiple inheritance while still providing much of the flexibility.

Pure virtual functions and the virtual table

Abstract classes still have virtual tables, as these can still be used if you have a pointer or reference to the abstract class. The virtual table entry for a pure virtual function will generally either contain a null pointer, or point to a generic function that prints an error (sometimes this function is named __purecall) if no override is provided.

12.7 -- Virtual base classes
12.5 -- The virtual table

145 comments to 12.6 — Pure virtual functions, abstract base classes, and interface classes

  • The Long

    Hi, Alex. Thank you for the great tutorial. One question, please:
    Why should we bother using/defining the interface class while in fact, all it ever does is just to show the definition of its own functions, and we have to explicitly deal with each version of implementation ourselves ?
    Wouldn't that be easier and more efficient to write the required functions without using the interface class? For example:

    why don't we just write: std::cout << "Tried to take square root of value less than 0" <<endl;  instead since I don't see cLog make any impact on the program at all except saying " We wasted memory for this object just to demonstrate that we are going to print an error meassage here".
    Much regard.

    • Alex

      The idea behind using an Interface class is that you can write code (such as a function) that works with any object that inherits that interface. In the case of IErrorLog, you don't have to care whether the error is being written to the console, to a disk, to a network location, to a database, or anywhere else. The caller can derive a class from IErrorLog and implement whatever behavior they want.

      This can be useful if you're writing code that's going to be used by other people, or that you want to be as reusable as possible for your own future uses.

      In the specific case where you only have one kind of error log, or just want to write an error to the console, this overhead isn't necessary.

      • The Long

        That means the Interface class is somewhat like a name card: just to show the caller what kind of work will be done. How the work is done and what result it produces is up to the caller to take care of, while the name card can be reused and placed wherever I want (legally). Is that right?

  • FS

    I believe this will work in Visual C++ only.
    This will not work with some compilers [ g++ for eg ] ,will cause a compiler error.
    We shouldn't use pure specifier [declaration] and the method body[definition] at same place.
    The correct way to define a body to Pure Virtual method is,
    Declare the method inside the class and define it outside with :: operator.


    • Alex

      Incorrect. Pure virtual functions with bodies are officially part of the C++ language (see, where Stroustrup notes that you can define a pure virtual function.

      Some compilers may not support them, but that is a deficiency of those particular compilers.

      • apfelpektin

        i got that error using gcc and read about it. i think FS is right.
        note that gcc allows pure virtual functions with definitions, but the declaration (with the '=0') must be separated from the definition (with the body, outside the class declaration).

        yes, "Pure virtual functions with bodies are officially part of the C++ language"
        but in your link Stroustrup is vague about that particular detail:

        "A virtual function is declared to be "pure" using the curious "=0" syntax."

        while a definition would also be a declaration and thus a definition including the '=0' would be ok, on the other hand he also uses an additional definition outside the class as a default implementation example:

        it looks rather that Visual C++ allows the '=0' pure virtual declaration at a definition.

        • Alex

          It appears you are correct. I've updated the lesson accordingly.

          Thanks for setting me straight on this. Information on this particular topic is pretty sparse.

  • Mauricio Mirabetti

    Alex, there are some typos on Pure virtual functions with bodies section. You are finishing speak() function definition with }; instead of }
    Best regards.

  • Maolin

    Hi Alex,

    why don't we want to make the destructor below also pure?

    thanks, Maolin

    • Alex

      As long as the destructor is virtual (which it is), when you delete a pointer to an IErrorLog object (or a reference to an IErrorLog goes out of scope), the virtual function resolution should happen and the proper derived destructors should be called. There's no need to make the destructor pure virtual unless you want to force derived classes to define their own destructor. Note that they can do this anyway if there's a specific reason to do so, so forcing the issue seems unnecessary.

  • Gajendra Gulgulia

    Hey Alex,

    I am a little confused here, on one hand it's mentioned in the tutorials that pure virtual functions should be defined without a function body, on the other hand the Dragonfly example has a default implementation in the pure virtual function in the base class. Am i missing something here?

    Thank you

    • Alex

      It's actually not the lack of a body that makes a function pure virtual, it's the = 0. Pure virtual functions are normally defined without a body, but as the Dragonfly example shows, you can add a body if you want to. The presence of absence of a body doesn't impact how the pure virtual function works, or its impact on the class (making it an abstract base class).

      I updated the Dragonfly example to indicate that it's the = 0 that makes the function pure virtual. Does that help clarify?

  • Jie

    Hi Alex, my codeblocks doesn't seem to allow pure virtual function to have a body, I got error for "virtual const char* speak() = 0 { return "buzz"; }, do you know why? Thanks!

    • Alex

      I presume your compiler simply doesn't support that feature. The good news is that pure virtual functions are rarely used with bodies, so even if your compiler doesn't support it, you're not missing out on too much.

      • Jie

        Thank you! Also I notice a small thing in 12.7, if I set the inheritance type to be virtual, for the initialization list in the constructor of Copier, I have to use () instead of {}, otherwise the Base constructor will be called three times. Is it a big deal? Or I should just remember the fact and not dig into the detail?

  • John

    The constructor is still accessible from within derived classes, making it possible to instantiate an Animal object.
    I'm trying to do it but gives me error. can you show me an example for that case.

  • joaquim

    i'm sorry, but can we override functions(from base) without redefinition on derived class?
    like these:


    • Alex

      Not sure what you're asking.

      • joaquim

        like you see, the 'getRate' ins't declared on Minigun class(so imagine if it's an object of Weapon). but the 'virtual' functions don't work on that way. so is there another type of functions that i can do it?
        thanks for all

        • Alex

          Oh, I see what you're asking. There's no way that I'm aware of to override a base function without redefining the function in a derived class. If you don't have access to Minigun, you could always derive your own class from Minigun and then provide a getRate() override function there.

  • J

    Question maybe a stupid one can you still declare a reference or pointer to a base abstract class that way you can do things like in previous lesson like point to different derived classes. Sorry If you already pointed this out

  • Elko

    Hi, nice tutorial.

    Just a tiny remark on the above quote:
    "Furthermore, although Java and C# will not let you use multiple inheritance on normal classes, they will let you multiply inherit as many interfaces as you like. Because interfaces have no data and no function bodies[...]"
    Since Java 8 there are method bodies in interfaces.

  • Alexander Bieniek

    "Furthermore, although Java and C# will not let you use multiple inheritance on normal classes, they will let you multiply inherit as many interfaces as you like."

    I'm familiar with this, I've used Interfaces in Java. However, does it get messy to try to use multiple interface classes in C++? It sounds kind of messy, especially given all of the problems that came up in the earlier lessons, like that diamond problem.

    ex: Say I wanted to make interface classes IConsumer and IGrower. Say IConsumer handles attainment of resources for an organism, and IGrower handles, well, changes in size or something. IConsumer and IGrower are not necessarily dependent on eachother and don't both need to be used, say in the case of a tree, which doesn't exactly consume anything.

    Anyway, would this kind of implementation get messy? Anything to keep in mind while trying to use multiple inheritence in a case like this?

    • Alex

      No, I don't think inheriting multiple interfaces is all that messy in C++. You aren't inheriting any member variables or default behaviors -- all you're really doing is promising that your class will fulfill the specification defined by the interface.

  • JaSoN

    Dear Alex, I still not clear about the Interface class, can you make another example? Thank for your tutorial

    • Alex

      Interface classes are just classes where all functions are pure virtual (abstract). Any derived class must provide implementations for all of the pure virtual functions in the interface class.

  • Devashish

    "any class with one or more pure virtual functions becomes an abstract base class, which means that it can not be instantiated"

    If we can't instantiate a base class that has a pure virtual function,

    isn't cLog an instance of interface class IErrorLog???

    • Alex

      Yes, this confusion is probably somewhat due to imprecise working on my part. You can't _directly_ instantiate any class that has pure virtual functions (which includes interface classes). You _can_ indirectly instantiate that class by instantiating a derived class that provides definitions for all the virtual functions in the base class.

      So yes, cLog is an instance of IErrorLog, but you can only pass objects of the derived class to it since there's no way to instantiate an object that is just an IErrorLog.

      Make sense?

  • vish

    how to remove ambuiguity here? or clear me if this is a bad coding
    using namespace std;
    class animal{
        string mname;

        animal(string a):mname(a){}
        const char* getspeak(){return "what";}

    class cow:virtual public animal{
        cow(string a):animal(a){}
        virtual const char* getspeak(){animal::getspeak();return  "moo";}
    class cat:virtual public animal {
        cat(string a):animal(a){}
        virtual const char* getspeak(){return "meow";}
    class pet:public cow,public cat{
        pet(string a,string b,string c):cow(b),cat(a),animal(c){}
    int main(){
    pet a("cow","cat","no");


    • Alex

      Your class hierarchy doesn't make sense. You're saying:
      * A cow is an animal -- okay, that's fine.
      * A cat is an animal -- okay, that's fine too.
      * A pet is both a cow and a cat simultaneously -- that's not correct!

      There are two ways to do what you want:
      1) Have both Animal and Pet both be base classes. Then Cat can inherit from Animal and Pet, and Cow can inherit from Animal (probably not Pet, since Cows usually aren't kept as pets).

      2) Since pet doesn't really do anything, it's probably better to make pet a virtual function: bool isPet(), that evaluates to true for Cat and false for Cow. That way you can avoid the multiple inheritance altogether.

      Also, Animal::getspeak() should be made virtual.

    • Steiner

      I'm just trying to give a technical answer on your question about removing ambiguity. Alex already gave an answer about redesigning this code.

      To remove the ambiguity, you have to use the scope resolution operator and pick from which derived class do you want to invoke getspeak().


  • Monic

    Is it okay if we do not write the pure virtual function for let's say function draw in figure base class, but we still write the draw function in the derived class?
    If so, then what is the advantage of writing the pure virtual function is base class if we can just write the function in every derived class?

  • for what purpose why we use abstract classes ????

  • Mariya

    How can we call a function with an argument of type reference to an object of an interface class if interface classes could not be instantiated? (I mean the example you give with the reference to IErrorLog.)

  • warzix

    Great article, although I should add one comment about the Interface class definition:

    "An interface class is a class that has no members variables, and where all of the functions are pure virtual! In other words, the class is purely a definition, and has no actual implementation."

    Effectively, my comment is after the example below:

    Suppose you define the following Interface

    class ISomething {
    virtual void doStuff1() = 0;
    //... bunch of other definitions

    and you have a class that implements it:

    class Impl : public ISomething {
    char* myCharPtr;
    void doStuff1() { /* do 'stuff' */ };
    // implement all other stuff
    /* Constructor that allocates memory */
    Impl() { myCharPtr = new char[10]; }
    /* Destructor that deallocates memory */
    ~Impl() { delete[] myCharPtr; }

    void main()
    ISomething* ptr = new Impl; //upcasting. ISomething pointer points to Impl object...

    delete ptr; //cleaning up memory...
    // This effectivelly invokes the default destructor on ISomething which is not virtual and therefore would not resolve to ~Impl()
    // therefore this can lead to memory leaks (as shown in the example) or any other problems related to missing destructor calls.

    I think it is worth a comment about that right after the phrase I've quoted such as:
    "The only exception is the destructor which should be virtual and implemented if the Interface is supposed to be used as a "placeholder" for pointers to derived classes' objects...".

    Best Regards

  • bantoo011

    How is the vtable for abstract & interface class looks like ?

    • Alex

      Abstract and interface classes usually still have virtual tables (these are used while the class is being constructed/destructed as part of a derived class, in case you call a virtual function from the constructor/destructor, which you should never do). The virtual table entry for a pure virtual function will generally either contain a null pointer, or point to a generic function that prints an error (sometimes this function is named __purecall).

  • saurabh

    I learned a lot from your tutorials and kudos to you

    It will be great if you can add two more topics to this chapter

    1) We can define body for a pure virtual function so please add when, why and how ?
    2) Please add virtual table view for abstract class why compiler not letting us to instantiate abstract class or i should say class having and pure virtual function

    Here is my views:
    we can not make object of abstract class because, in the vtable the vtable entry for the abstract class functions will be NULL, even if there is a single pure virtual function in the class the class becomes as abstract class.Even if there is a single NULL entry in the function table the compiler does not allow to create the object.

    • Alex

      1) I've updated the lesson to include a subsection talking about pure virtual functions with bodies.
      2) The virtual table entry for a pure virtual function will generally either contain a null pointer, or point to a generic function that prints an error (sometimes this function is named __purecall).

      The compiler disallows you from instantiating an abstract base class because it knows which classes are abstract and which aren't. It doesn't need to worry about virtual tables to determine that.

  • Kathy

    petrfect tutorial~~

    I have learned a lot...

  • ricky

    just a simple program..


    my doubt:

    How am I able to access the private member of derived class function (**which is private) using base class pointer??

    • Sushant Choudhary

      your bptr->display() actually dissolves internally to bptr->derived's vptr->display(), now since vptr is public in base which gets derived publically in derived as well so vptr can call display().

      You need to understand how vtable and vptr works.

  • LJ

    this is definitely the best tutorial i've found so far on c++. great work!
    another quick nitpick: the mySqrt function does not take the square root :)

  • sudheer

    Wonderful tutorial on Pure Virtual functions. Kudos Alex


    I have read 2 other tutorials and this one is the one that has "everything".

  • Balaji

    Very good tutorial for beginers,

  • Ben

    Hi Alex,
    in your IErrorLog class all functions are private. As i tried to compile your code, with the MySqrt() function, i discoverd, that the compiler complains about that, so i defined a class inheriting IErrorLong and changing the scope of the functions to public; still the compiler insists not to compile the code. So you might want to change the code. Besides that, can you imagine why a virtual class should ever have private member functions?

    • Hi Ben,

      I agree with you, the functions need to be public. My code did compile - the only thing
      I needed to be sure about was that the IErrorLog parameter to MySqrt was a pointer or reference.
      If it's passed by value the compiler tries to instantiate an IErrorLog object which it can't do for an abstract class.


    • Alex

      I've updated IErrorLog so that all of the members are public.

      C++ will allow you to have private virtual functions, and to override them in derived classes. Are they useful? They can be in specific situations. See this wikipedia article on Non-virtual interfaces, which make use of pure virtual private functions.

  • Sean

    Great tutorial for interface class,
    Thanks a lot!

  • Susan

    Can you please answer why a pure virtual function should be equated to 0 and not to any other number.

    • As far as I know, =0 is just a syntactic convention for letting the compiler know that this is a pure virtual function.

      You can think about it this way: normal functions have a body of code that needs to be executed when they are called. This code has to live somewhere in memory, so the function's name is essentially a pointer to that code.

      On the other hand, pure virtual functions have no body, and thus, do not have need for an address at all. 0 is the NULL address.

    • Jim

      I read this today, they didn't want to add any more reserved words such as "pure" and it was moving too far from the C language, so this hotchpotch =0 stuff was used instead

    • w0rkbean

      As someone said earlier, it's a syntactic convention. I think the reason for that convetion can be explained as " as we know the function name itself is a pointer to that function just like array name is a pointer to the first element of that array. So if you are equating that pointer to 0 which is a NULL, makes it a NULL pointer". So the essence is equating the function to 0 is like defing a NULL ponter which may point to a a valid address later on"

Leave a Comment

Put all code inside code tags: [code]your code here[/code]