C + + virtual inheritance

Keywords: C++ Attribute

Suppose we have class A, class B and class Test. Class Test has all the attributes of class A and class B, and they all have the temp attribute. Now we need to set and read the temp attribute in class Test, so write the following program:

#include <iostream>

class Base{
public:
    int temp;
};

class A : public Base{
};

class B : public Base{
};

class Test : public A, public B{
public:
    void setValue(int val){
        temp = val;
    }

    void print(){
        std::cout << temp << std::endl;
    }

};

int main()
{
    Test T = Test();

    T.setValue(1004);
    T.print();

    return 0;
}

It took a lot of effort to write the program, but after saving it, the compiler actually hung 0.0

This is because multiple inheritance makes the base class copy many times. At last, when the subclass calls the same property, it will cause ambiguity.

For the above program, we can change it to pass compilation as follows:

class Test : public A, public B{
public:
    void setValue(int val){
        A::temp = val;
    }

    void print(){
        std::cout << B::temp << std::endl;
    }

};

The program output is 0.

This solves the problem of ambiguity, but this kind of code appears bloated, and the same attributes are copied many times will waste memory.

Virtual inheritance can easily solve the above problems. The subclass still inherits the base class, but at this time, it is not a copy of memory, but a pointer to the base class, which occupies a memory of pointer.

The virtual inheritor is as follows:

#include <iostream>

class Base{
public:
    int temp;
};

class A : virtual public Base{
};

class B : virtual public Base{
};

class Test : public A, public B{
public:
    void setValue(int val){
        temp = val;
    }

    void print(){
        std::cout << temp << std::endl;
    }

};

int main()
{
    Test T = Test();

    T.setValue(1004);
    T.print();

    return 0;
}

The application of virtual inheritance not only solves the problem of ambiguity, but also the problem of waste of resources~

reminder:

Although virtual inheritance is good, it can't be greedy. In the development process, we should avoid using multiple inheritance, which will make the program more complex, so the possibility of error is higher.

Supplementary virtual inheritance memory occupation size (32-bit machine, from Encyclopedia):

#include <iostream>  

using namespace std;  
  
/* Size 4 */
class A
{  
public:  
    int a;  
};  

/* Size 12, variable a,b 8 bytes in total, virtual base class table pointer 4 */
class B :virtual public A  
{  
public:  
    int b;  
};  

/* Like B, 12 */
class C :virtual public A  
{  
public:  
    int c;  
};  

/* 24,Variable a,b,c,d 16 in total, virtual base class pointer 4 of B, virtual base class pointer 4 of C */
class D :public B, public C  
{  
public:  
    int d;  
};  
  
int main()  
{  
    A a;  
    B b;  
    C c;  
    D d;  
    
    cout << sizeof(a) << endl;  
    cout << sizeof(b) << endl;  
    cout << sizeof(c) << endl;  
    cout << sizeof(d) << endl;  

    return 0;  
}

Posted by Japet on Mon, 06 Apr 2020 10:45:40 -0700