Parent Pointer

Hallo C++'ler!

Ich habe Schwierigkeiten mit einer ganz einfachen Sache:
Seien dies die Klassen:
DATA , LIST, und ITEM

DATA hat ein Member LIST*
LIST hat ein Member NODE*
NODE ist eine Struktur mit einem ITEM*

Jetzt möchte ich das jedes ITEM eine Verweis auf DATA hat
(den Haupt-Parent sozusagen).

Beim Compilieren gibt es aber dahingehend Probleme, das er DATA*
nicht kennt, wegen der #Include „… .h“ - Kette:
DATA -> include „LIST.h“
LIST -> include „ITEM.h“
ITEM -> include „DATA.h“ (wegen des Parent Pointers)

ITEM braucht DATA und umgekehrt.

Jetzt habe ich versucht einen untypisierten Pointer als Parent
zu speichern (void* oder sowas). Irgendwann hab ich gar nichts
mehr verstanden.

Wie macht man das richtg ?
Danke und Happy C’ing.

Hallo Bernd!

Ich kenne diese Probleme nur zu gut, falls ich dich richtig verstanden habe. Du hast in deinen Includierungen einen Zirkelbezug, da das eine schon definiert sein sollte obwohl es erst später mich selber braucht…

Lösung:

Das Problem bei großen Projekten ist ja sowieso, dass man soooo viele Headerdateien hat - und deshalb schreib ich einfach eine Datei namens AllInc.h, welche alle Dateien includiert, die ich brauche (abgesehen von der stdafx.h, die braucht man in jeder .cpp wegen der vorkompilierten Headerdatei). In jeder cpp steht also am Anfang:

#include „stdafx.h“
#include „AllInc.h“

Jetzt muss man halt schauen, dass in der AllInc.h die richtige Reihenfolge eingehalten wird beim includieren der einzelnen Headerdateien! Das macht man so:

* Du includierst alle Headerdateien, wie gesagt.

* Du compilierst (nur) deine erste cpp.
Die positionierst deine Headerdateien so, dass der angezeigte Fehler, falls vorhanden weg ist. Dann compilieren, dann wieder verschieben, bis alles OK ist für diese cpp-Datei.

* Danach machst du das für die nächste cpp, dann für die nächste usw.

Es ist vielleicht keine Hollywood-Methode, aber: Es funktioniert.
Einen weiteren Vorteil hat diese Methode noch, da bei einer neuen Datei, einfach die AllInc.h hinzugefügt wird und in der AllInc.h die neue Headerdatei eingefügt wird - Und schon ist überall deine neue Datei bekannt und deine neue Datei kennt alles Andere.

Viel Glück beim Includieren,
KoRn!

Danke schön. Ich werde es gleich mal versuchen.
Zwischenzeitlich hatte ich eine (fast-)Lösung:
Anstelle der typisierten Zeiger habe ich void* verwendet.
Wenn ich das Objekt irgendwo brauche, dann konvertiere
ich es zu
…=(DATA*) data->parent;

Das dumme ist nur, das ich den parent ja dort speichere, wo
ich ihn brauche und ansprechen will, d.h in ITEM, und dort
kennt er ja DATA nicht. ätsch.

Gruss,
Bernd

Hallo Bernd,

im Normalfall brauchst Du im Header nicht die komplette Klassendeklaration. So gehts auch:

eins.h :

class ZWEI;

class EINS {
 ZWEI\* pZwei;
 ...
};

zwei.h :

class EINS;

class ZWEI {
 EINS \*pEins;
 ...
};

Erst in der/den .cpp-Datei(en) steht dann ein

#include "eins.h"
#include "zwei.h"

und alles wird gut…

Hoffe geholfen zu haben und Gruß,
Ralf

Das Problem mit den Includedateien kann man noch einfacher umgehen. Baue Deine Include Dateien einfach mal so auf:

#ifndef __irgendeinname__
#define __irgendeinname__

#include „anderedatei.h“
Hier ist der ursprüngliche Teil der Include-datei

#endif

So das wars.
Wenn Die Include datei diese Zeilen enthält, dann wird sie nur einmal includiert. Jetzt kannst Du in der Headerdatei includieren was Du willst, auch das gegenseitige includieren funktioniert. Ich schreib diese 3 Zeilen grundsätzlich immer in eine Includedatei, dann hat man schließlich überhaupt keine Probleme mehr.
Funktionieren tut das so:
Mit #ifndef fragt man ab ob die darauf folgende Zeichenkette schon definiert ist. Falls nicht dann wird sie definiert und der eigentliche Code der Include-Datei folgt. Falls das Zeichen schon definiert ist dann springt der Compiler zur Zeile #endif, damit wird gar nicht includiert. Wenn nun der Compiler das erste mal in Deiner Datei ankommt, dann wird die Header-Datei includiert, die includiert dann deine zweite Datei, die zweite Datei includiert dann blöderweise die erste Datei. In der ersten Header-Datei wieder angekommen merkt der Compiler dann, daß die Zeichenkette schon definiert ist und überspring die Include-Datei: Problem tritt somit nicht auf.

mfg
Marco

Die Bezeichner __irgendeinname__ müssen natürlich in jeder Includedatei anders sein. Im normalfall nehme ich immer den Dateinamen der includedatei: __dateiname__h__

mfg
Marco

Ja das habe ich aber auch gemacht. Genau wie Du beschrieben hast, und zwar in jeder Header Datei.
Das Projekt ist recht gross. Irgendwie ging es aber nicht,
da sich am Anfang der Header Datei
eine #include „andere_datei.h“ befindet, und er erst weiter
compiliert, wenn die „andere_datei.h“ übersetzt ist.
Da steht aber eine #include „ersteDatei.h“, und zack geht’s
nicht, da er die Typen/ Klassen die dort definiert werden
noch nicht kennt.
Ich habe mich damit zufrieden gegeben, alle infos, die ich
von dem Objekt brauche (dessen Verweis ich speichern wollte)
von Kontruktor entgegen nehme, und hoffe das es nicht zu viele
sind…

Trotzdem Danke.
Gruss,
Bernd

[Bei dieser Antwort wurde das Vollzitat nachträglich automatisiert entfernt]

Ich würde die Includes erst nach dem #ifndef - #define einfügen