Zugriff auf Basisklasse in dynamischer Unterklasse



  • Vielen Dank, ich habe es in der vorgeschlagenen Form geändert. Nun kann ich jedoch nicht mehr von der Basisklasse auf die entsprechende Unterklasse zugreifen 😞

    Ich habe nämlich in Linie.h folgende Funktion:

    void Linie::show_linie(Linie* init_linie, string init_str_variantenart)
    {
    	init_linie->richtung_fw->show_linienrichtung(init_linie->richtung_fw, init_str_variantenart);
    	init_linie->richtung_bw->show_linienrichtung(init_linie->richtung_bw, init_str_variantenart);
    }
    

    Nun wird nicht mehr erkannt, dass "richtung_fw" ein Element der Unterklasse "Linienrichtung" ist.
    Ich bekomme die Fehlermeldungen

    error C2027: Verwendung des undefinierten Typs "Linienrichtung"

    und

    error C2227: Der linke Teil von '->show_linienrichtung' muss auf Klasse/Struktur/Union zeigen

    Hast Du dafür noch eine Idee?

    Vielen Dank!

    Andy



  • Die Implementierung der Klassen in eigene cpp's und dann in linie.cpp #include "linienrichtung.h".



  • Im großen und ganzen sollte das alles so aussehen:

    linie.h

    #ifndef __LINIE_
    #define __LINIE_
    
    class Linierichtung; //Forward-Deklaration
    
    class Linie {
    ...
    };
    
    #endif
    

    linienrichtung.h

    #ifndef __LINIENRICHTUNG_
    #define __LINIENRICHTUNG_
    
    #include "linie.h"
    
    class Linierichtung : public Linie {
    ...
    };
    
    #endif
    

    linie.cpp

    #include "linie.h"
    #include "linienrichtung.h"
    
    void Linie::show(...) { }
    // blabalb der Rest auch
    

    linienrichtung.cpp

    #include "linienrichtung.h"
    
    //blablabla
    


  • Ich habe immer gedacht, dass __ (Doppel-Unterstrich) in den Includeguards böse ist. Sogar sehr böse. 😕



  • Danke noch mal, aber jetzt bekomme ich auf einmal 116 Buildfehler angezeigt! 😞

    Der erste Fehler tritt in Linienrichtung.cpp auf und besagt, dass die Elemente der Klasse Linienrichtung nicht gefunden werden.

    Linienrichtung.cpp:

    #include "Linienrichtung.h" 
    
    void Linienrichtung::show_linienrichtung(Linienrichtung* init_linienrichtung, string init_str_variantenart) 
    {
        cout << "  " << init_linienrichtung->val_name << " -> Ri. " << init_linienrichtung->val_hauptziel << endl;
        //...
    }
    

    "val_name" und "val_hauptziel" sollen hier angeblich keine Elemente von "Linienrichtung" sein, obwohl sie ja in Linienrichtung.h definiert sind...

    Ich blicke hier wirklich nicht mehr durch 😕

    Noch eine Idee? 😉

    Grüße

    Andy



  • Hmmm, ist überhaupt show_linienrichtung(...) in der Klasse deklariert ???



  • Freak_Coder schrieb:

    Hmmm, ist überhaupt show_linienrichtung(...) in der Klasse deklariert ???

    Ja, ist es... Aber ich glaube, ich lasse es jetzt lieber so wie es war und speichere die Liniennummer der Basisklasse noch mal in der Unterklasse "Linienrichtung". Ist dann zwar redundant, aber das Problem scheint wohl recht kompliziert zu sein 😉

    Trotzdem danke 😉

    Andy



  • Zeig doch mal etwas mehr Code (vor allem - wer includiert was und wo?) Denn eigentlich müsstest du imho Zugriff auf die Basiselemente haben.

    Ansonsten solltest du mal über dein Design nachdenken - eine Linie hat/kennt zwei Richtungen - eine Richtung ist eine Linie -... irgendwo drehst du dich da im Kreis.



  • sCIfI->na schrieb:

    Ich habe immer gedacht, dass __ (Doppel-Unterstrich) in den Includeguards böse ist. Sogar sehr böse. 😕

    Du hast recht. Es ist ein Fehler.



  • CStoll schrieb:

    Ansonsten solltest du mal über dein Design nachdenken - eine Linie hat/kennt zwei Richtungen - eine Richtung ist eine Linie -... irgendwo drehst du dich da im Kreis.

    Ja, das kommt mir auch so vor. Allerdings muss ich auch dazu sagen, dass dies mein erstes Projekt ist, in dem ich Klasseneigenschaften vererbe. Jedoch müsste es doch schon möglich sein, von einer Linie auf ihre beiden Fahrtrichtungen zuzugreifen und gleichzeitig auch von einer Fahrtrichtung auf ihre übergeordnete Linie?

    Jedenfalls hier mein Code. "Linienvariante" ist eine Unterklasse zu "Linienrichtung", "Linienverlauf" eine Unterklasse zu "Linienvariante".

    Hauptdatei (.cpp):

    #include <iostream>
    #include <iomanip>
    #include <windows.h>
    #include <sql.h>
    #include <sqlext.h>
    #include <string>
    #include <vector>
    #include <list>
    #include <iostream>
    #include <fstream>
    #include <sstream>
    #include <time.h>
    
    #include "consts.h"
    #include "mt-rand.h"
    #include "Ort.h"
    #include "Strecke.h"
    #include "Linienverlauf.h"
    #include "Linienvariante.h"
    #include "Linienrichtung.h"
    #include "Linie.h"
    
    //...
    
    class Daten 
    {
    public:
    	Daten();
    	void main(void);
    private:
    	void set_verbindungsparameter(const string init_str_URI, const string init_str_user, const string init_str_passwort);
    	void init(void);
    	void get_orte(void);
    	void get_strecken(void);
    	void get_strecken_hp(void);
    	void get_streckenfahrzeiten(void);
    	void get_linien(void);
    	Linienrichtung* get_linienrichtung(Linie* tmp_linie, string tmp_richtung);
    	vector<Linienvariante*> get_linienvarianten(Linienrichtung* init_linienrichtung, string init_richtung);
    	void get_linientakte(Linienvariante* init_linienvariante);
    	Linienverlauf* get_linienverlauf(Linienvariante* init_linienvariante);
    
    	void add_strecke_hp(const Strecke* strecke1, const Strecke* strecke2, const Strecke* strecke3);
    	string ersetze_umlaut(string name, string umlaut);
    
    	void show_orte(void);
    	void show_strecken(vector<Strecke*>);
    	void show_linien_alle(void);
    	void show_linien_aktiv(void);
    	void show_error(ostringstream &oss, int prio);
    
    	SQLRETURN lese_daten(string str_sql);
    
    	//Verbindungsdaten für ODBC-Datenbank
    	string str_URI;
    	string str_user;
    	string str_passwort;
    
    	//ODBC-Verbidungshandles
    	SQLHANDLE hEnvironment;
    	SQLHANDLE hConnection;
    	SQLHANDLE hStatement;
    
    	Netzwerk MyNetzwerk;
    	vector<Linienverlauf*> vec_linienverlaeufe;
    
    	string str_pfad_errorlog;
    	int anz_datenfehler;
    };
    
    //...
    
    void Daten::get_linien(void)
    {
    	//...
    
    	//hier wird eine Linie erstellt
    	for (unsigned int i=0; i<anz_datensaetze; i++) {
    		Linie* akt_linie = new Linie(arr_linien[i].iLINIE_NR);
    		MyNetzwerk.vec_linien.push_back(akt_linie);
    	}
    }
    

    Linie.h

    #ifndef _LINIE
    	#define _LINIE
    
    using namespace std;
    
    class Linienrichtung;
    
    class Linie
    {
    public:
    	const int val_liniennr;
    	int anz_varianten_aktiv;
    
    	Linienrichtung* richtung_fw;
    	Linienrichtung* richtung_bw;
    	void show_linie(Linie* init_linie, string init_str_variantenart);
    
    	Linie(const int tmp_liniennr) 
    		: val_liniennr(tmp_liniennr) {
    			anz_varianten_aktiv = 0;
    	}
    };
    
    #endif
    

    Linie.cpp:

    #include "Linie.h"
    #include "Linienrichtung.h" 
    
    void Linie::show_linie(Linie* init_linie, string init_str_variantenart)
    {
    	cout << "Linie " << setw(2) << init_linie->val_liniennr << ": " << endl;
    	cout << "  " << init_linie->anz_varianten_aktiv << " aktive Varianten" << endl;
    	init_linie->richtung_fw->show_linienrichtung(init_linie->richtung_fw, init_str_variantenart);
    	init_linie->richtung_bw->show_linienrichtung(init_linie->richtung_bw, init_str_variantenart);
    }
    

    Linienrichtung.h:

    #ifndef _LINIENRICHTUNG
    	#define _LINIENRICHTUNG
    
    #include "Linie.h"
    
    using namespace std;
    
    class Linienrichtung : public Linie
    {
    public:
    	const string val_name;
    	const string val_hauptziel;
    	int anz_varianten;
    	int anz_varianten_aktiv;
    	vector<Linienvariante*> vec_linienvarianten;
    	void show_linienrichtung(Linienrichtung* init_linienrichtung, string init_str_variantenart);
    
    	Linienrichtung(const string tmp_name, const string tmp_hauptziel) 
    		: val_name(tmp_name), 
    		val_hauptziel(tmp_hauptziel) {
    			anz_varianten = 0;
    			anz_varianten_aktiv = 0;
    	}
    
    	Linienrichtung(const string tmp_name, const string tmp_hauptziel, const int tmp_liniennr)
    		: val_name(tmp_name), 
    		val_hauptziel(tmp_hauptziel) : Linie(tmp_liniennr) {
    			anz_varianten = 0;
    			anz_varianten_aktiv = 0;
    	}
    };
    
    #endif
    

    Linienrichtung.cpp:

    #include "Linienrichtung.h" 
    
    void Linienrichtung::show_linienrichtung(Linienrichtung* init_linienrichtung, string init_str_variantenart) 
    {
        cout << "  " << init_linienrichtung->val_name << " -> Ri. " << init_linienrichtung->val_hauptziel << endl;
    	cout << "    " << init_linienrichtung->anz_varianten_aktiv << " aktive " << init_linienrichtung->val_name << "-Varianten" << endl;
    	for (int i=0; i<init_linienrichtung->vec_linienvarianten.size(); i++) {
                //...
    	}
    }
    

    Grüße

    Andy


Anmelden zum Antworten