C++ Kompilierzeiten optimieren

Der ein- oder andere von euch wird das wohl kennen. Ihr arbeitet an einem Projekt und ändert etwas an einer Header-Datei. Ihr fügt z. B. eine neue Variable hinzu. Danach kompiliert das ganze Projekt erstmal wieder 2 Minuten, obwohl ihr nicht wirklich viel gemacht habt. Ich habe schon seit einer ganzen Weile einen Artikel auf meiner Leseliste und bin nun endlich dazugekommen ein wenig rein zu lesen.

In dem Artikel wird einfach erklärt was (so ungefähr) beim kompilieren und linken von C++-Projekten passiert und wie man dies unter Umständen ein wenig optimieren kann.

Ein ziemlich einfacher Lösungsansatz, der ziemlich wirkungsvoll sein kann und von dem ich mich Frage wieso ich eigentlich selbst noch nicht darauf gekommen bin möchte ich euch heute zeigen: Forward-Deklaration

Hier ein kleines Beispiel:

// a.h
class A
{
   // Deklarationen
   // Funktionen
   // etc.
};

// b.h
#include "a.h"
class B
{
   A a;
};

Hier ist die Klasse A per include in der Klasse B eingebunden. Wird nun in der Klasse A z. B. eine neue Variable oder Funktion hinzugefügt wird auch die B neu kompiliert. Wie kann man das umgehen? Wie vorher schon erwähnt mit einer Forward-Deklaration:

// a.h
class A
{
   // Deklarationen
   // Funktionen
   // etc.
};

// b.h
class A;

class B
{
   A *a;
};

Wer sich die beiden Beispiele genau angesehen hat, sieht: A ist jetzt ein pointer. Wieso? Mit der Forward-Deklaration sagen wir dem Compiler nur „Hey, es gibt die Klasse A!“, mehr weiß dieser aber zu diesem Zeitpunkt nicht, er weiß also nicht wie viel Speicher er dafür allokieren muss, etc..
In der cpp muss die Header-Datei von A dann bei Bedarf natürlich auch eingebunden werden.

Natürlich kein Post ohne einen Test. Bei einem Projekt das ~5 Minuten kompiliert dauert das neue kompilieren nach einer Änderung gute 2 Minuten. Nach dem Umbau auf Forward-Deklarationen und der gleichen Änderung dauert das erneute kompilieren nur noch gute 40 Sekunden, also weniger als die Hälfte!

Schreibe einen Kommentar

Deine E-Mail-Adresse wird nicht veröffentlicht. Erforderliche Felder sind mit * markiert.