2016-04-19 2 views
1

Ich verwende vs2013 (Win32) Testen der folgenden Programm:Wie viel Platz kostet eine Derived-Klasse? Wenn sie selbst und ihre Basisklasse beide über virtuelle Methoden verfügen?

#include <iostream> 

class A { 
    virtual void funA(); 
}; 

class B { 
    virtual void funB(); 
}; 

class C :public A{ 
    int i; 
    virtual void funC(); 
}; 

class D :public B, C{ 
    virtual void funD(); 
}; 

int main(){ 
    std::cout << "size A " << sizeof(A) << std::endl; 
    std::cout << "size B " << sizeof(B) << std::endl; 
    std::cout << "size C " << sizeof(C) << std::endl; 
    std::cout << "size D " << sizeof(D) << std::endl; 
    return 0; 
} 

Und das Ergebnis ist

Größe A 4
Größe B 4
Größe C 8
Größe D 12

Warum Größe (C)! = 8 + Größevon (A) und Größevon (D)! = 4 + Größevon (B) + Größevon (C)?

Antwort

6

A ist eine einzelne Basisklasse mit virtuellen Methoden, daher ein einzelner vtable-Zeiger, also 4 Bytes auf einer 32-Bit-Plattform wie deins.

B ist genau wie A.

C ist wie A plus eine 4-Byte-Ganzzahl. Beachten Sie, dass es immer noch nur eine einzige Basisklasse (A) gibt, was noch immer nur einen Vtable-Zeiger bedeutet.

D erbt von zwei Basisklassen mit virtuellen Methoden, die nicht miteinander verwandt sind, erhält somit zwei Dvtable Zeiger (eine für jede Basisklasse), zuzüglich die 4-Byte-Ganzzahl von C. Also insgesamt 12 Bytes.

+0

Warum C und D keinen eigenen Vtable-Zeiger haben? @John Zwinck –

+0

@YuanWen Sie brauchen nicht, sie brauchen nur größere Tabellen. – molbdnilo

+0

@YuanWen, vtable Zeiger wird verwendet, um zu bestimmen, welche virtuelle Methode für bestimmte Instanz verwendet werden soll (ob es sich um eine Instanz der Basis oder eine der abgeleiteten Klassen handelt). –

Verwandte Themen