Search code examples
c++inheritancevirtual

Virtual inheritance: No matching function for call to


I've got the following code. This code serves the purpose to

#include <stdio.h>
#include <iostream>
struct A {
    public:
        virtual void m1(){
            std::cout << "A virtual void m1"<<std::endl;
        }
        void m1(int a){
            std::cout << "A void m1(int)"<<std::endl;
        }
        virtual void m2(){
            std::cout << "A virtual void m2()"<<std::endl;
        }
        void m3(int a){
            std::cout << "A void m3(int)"<<std::endl;
        }
};
struct B: virtual  A{
    public:
    B():A(){}
    virtual void m1(){
        std::cout <<"B virtual void m1()" <<std::endl;
    }
    virtual void m2(int a){
        std::cout << "B virtual void m2(int a)"<<std::endl;
    }
    void m3(){
        std::cout <<"B void m3" <<std::endl;
    }
    virtual void m4(){
        std::cout <<"B void m4()" <<std::endl;
    }
};



int main() {
    B* b = new B;

    b->m1();
    b->m1(1);
    b->m2();
    b->m3(1);

    return 0;
}

When I try to compile said code I get the following errors:

$ c++ virtual.cpp
virtual.cpp: In function ‘int main()’:
virtual.cpp:90:12: error: no matching function for call to ‘B::m1(int)’
     b->m1(1);
            ^
virtual.cpp:21:18: note: candidate: ‘virtual void B::m1()’
     virtual void m1(){
                  ^~
virtual.cpp:21:18: note:   candidate expects 0 arguments, 1 provided
virtual.cpp:91:11: error: no matching function for call to ‘B::m2()’
     b->m2();
           ^
virtual.cpp:24:18: note: candidate: ‘virtual void B::m2(int)’
     virtual void m2(int a){
                  ^~
virtual.cpp:24:18: note:   candidate expects 1 argument, 0 provided
virtual.cpp:92:12: error: no matching function for call to ‘B::m3(int)’
     b->m3(1);
            ^
virtual.cpp:27:10: note: candidate: ‘void B::m3()’
     void m3(){
          ^~
virtual.cpp:27:10: note:   candidate expects 0 arguments, 1 provided

After reading about virtual functions, I'd for example expect my call b->m1(1) to resolve to B::m2(int a) but evidendly my code is wrong.

I suspect that I'm not initializing the parent structs correctly, but other than I have no clue what I am doing wrong.


Solution

  • When you overload an inherited function in C++, the base class functions with the same name are hidden. Hidden base class functions cannot be called like class functions or not hidden inherited functions, you need to specifically tell the compiler that you want to use the hidden function.

    You do that writing down the class that defines the function you want to use: theRightClass::ambiguousFunction();

    In your code, the main function becomes:

    int main() {
        B* b = new B();
    
        b->m1();
        b->A::m1(1);
        b->A::m2();
        b->A::m3(1);
    
        delete b;
    
        return 0;
    }