Cost of unnecessary virtual inheritance

Is there any time or space penalty from inheriting virtually when not needed? For example, consider (x->y means "y inherits from x") A -virtual-> B -> C, where there are no other classes in the program. How does this compare to A -> B -> C?
Is there any time or space penalty from inheriting virtually

Most likely, yes for both. If there are virtual functions there will be a need for virtual tables which increases both to some degree.

Like the rest of C++ if you don't need a feature don't use it and you will probably save on one or the other or both.

You may be interested in this SO topic: https://stackoverflow.com/questions/7210412/what-is-the-cost-of-inheritance
Last edited on
Most likely, yes for both.
I can make guesses on my own. I don't need to ask anyone to know that it might have a cost. I want to know if it actually has a cost.

If there are virtual functions there will be a need for virtual tables which increases both to some degree.
Virtual functions are orthogonal to virtual inheritance. You can have neither, both, or just one of the two.

Like the rest of C++ if you don't need a feature don't use it and you will probably save on one or the other or both.
I'm asking because in my case I need to generate class definitions from a high-level description, and it turns out that deciding whether a particular inheritance should be virtual or not from an inheritance graph (a DAG) is non-trivial. If the compiler generates code and memory layouts in such a way that inheriting virtually when not needed has basically no cost then I can just always inherit virtually and forget about the problem.

You may be interested in this SO topic: https://stackoverflow.com/questions/7210412/what-is-the-cost-of-inheritance
The question is about virtual inheritance compared to non-virtual inheritance, not inheritance compared to non-inheritance.

Please don't answer if you don't have an answer to the question.
Yes, there is a cost.

Both in size

1
2
3
4
5
6
7
8
9
10
11
#include <iostream>

struct B {int n;};
struct D1 : B {};
struct D2 : virtual B {};

int main()
{
	std::cout << "sizeof(D1) = " << sizeof(D1) << '\n';
	std::cout << "sizeof(D2) = " << sizeof(D2) << '\n';
}
sizeof(D1) = 4
sizeof(D2) = 16
http://cpp.sh/9pudf

and in runtime performance

1
2
3
4
5
6
7
8
9
10
11
12
13
14
struct B {int n;};
struct D1 : B {};
struct D2 : virtual B {};

void f(D1& d1)
{
	d1.n = 10;
}

void f(D2& d2)
{
	d2.n = 10;
}




f(D1&):
    mov DWORD PTR [rdi], 10
    ret


f(D2&):
    mov rax, QWORD PTR [rdi]
    mov rax, QWORD PTR [rax-24]
    mov DWORD PTR [rdi+rax], 10
    ret
https://godbolt.org/g/sgej54
Darn. Thanks.
Topic archived. No new replies allowed.