Cast von Objekten?



  • Hallo,
    vielleicht habe ich gerade ein Konten im Kopf aber ich verstehe folgendes Problem nicht :

    #include <iostream>
    class parent{
    public:
    	virtual void A(){
    	}
    
    };
    typedef parent *parentP;
    
    class child : public parent{
    public:
    	void A( int a, int b);	
    
    };
    typedef child *childP;
    
    class childA : public parent{
    	void A(int a, int b, int c);
    
    };
    
    void child::A(int a, int b){
    	std::cout<< "child A:" << a << " B: " << b << std::endl;	
    }
    
    void childA::A(int a,  int b, int c){
    	std::cout<< "child 2 A:" << a << " B: " << b << " C: " << c << std::endl;	
    }
    
    int main(void){
    	parentP ptr;
    	ptr =  new child;
    	ptr->Init(2,3); 
    ...
            delete ptr;
    }
    

    bei der Zeile ptr->Init(2,3) meckert der comp. das er keinen passenden Funktionsaufruf findet. 😕
    Ich habe im Original ein Parent Obj und mehrer Derivate und diese werden jetzt je nach Maschinentyp zugewiesen wärend der Laufzeit.
    Ist das so oder so ähnlich überhaupt möglich?



  • Es gibt in deinem Code keine Funktion Init.
    Es wird nirgends gecastet.
    Niemand will wissen, ob du die indirekte Rede beherrschst. Fehlermeldung: Copy&Paste.



  • Entweder du implementierst in Klasse parent eine Methode ::Init( int a, int b) oder änderst die Zeile 33 in: ptr = new child( 2, 3 );



  • ahh. ich meinte :
    zeile 33: ptr->A(2,3);
    sorry ursprünglich hieß die Methode Init, habe sie dann abstrahiert.
    leider funktioniert das trotzdem nicht...

    Fehlermeldung..
    [Error] no matching function for call to 'child::child(int, int)'



  • 1. Zeig den kompilierten Code
    2. Zeig die vollständige Fehlermeldung dazu



  • #include <iostream>
    class parent{
    public:
    	virtual void A(){
    	}
    
    };
    typedef parent *parentP;
    
    class child : public parent{
    public:
    	void A( int a, int b);	
    
    };
    typedef child *childP;
    
    class childA : public parent{
    	void A(int a, int b, int c);
    
    };
    
    void child::A(int a, int b){
    	std::cout<< "child A:" << a << " B: " << b << std::endl;	
    }
    
    void childA::A(int a,  int b, int c){
    	std::cout<< "child 2 A:" << a << " B: " << b << " C: " << c << std::endl;	
    }
    
    int main(void){
    		parentP ptr = *new childP();
    		ptr->A(2,3);
    		delete ptr;
    }
    

    [Error] no matching function for call to 'parent::A(int, int)',



  • ~~Hallo,

    die Klasse Parent hat ja auch keine Funktion A. So funktioniert das nicht.
    Vielleicht willst du eine virtuelle basis-funktion A in Parent und in den children überschreiben?~~

    Man bin ich müde, thx daddy_felix



  • Jockelx schrieb:

    die Klasse Parent hat ja auch keine Funktion A.

    Das schon. Nur eben keine, die zwei int Parameter erwartet.



  • Da sind mehrere Dinge drin.

    1. Lass deine komischen Pointer-Typedefs weg: typedef parent *parentP; - Sie verwirren dich später nur, wie man am "new" sieht.

    2. Wenn eine Funktion pure virtual sein soll, d.h. virtuell, aber du willst in der Basisklasse noch keine Implementierung vornehmen, dann schreib:
    virtual void A() = 0;

    3. Wenn du die Funktion A() als virtuell deklarierst, ist NICHT automatisch die Funktion A(int) , A(int, int) oder A(int, int, int) auch virtuell. Das virtual wirkt sich nur auf Funktionen mit DERSELBEN Signatur aus. Wenn du eine virtuelle Funktion in der Child-Klasse implementieren willst, nutze "override", um sicherzustellen, dass die passende Funktion in der Basisklasse als "virtual" deklariert worden ist.

    4. Deine Basisklasse benötigt einen virtuellen Destruktor!

    5. Dein main:

    int main(void){
            parentP ptr = *new childP();
            ptr->A(2,3);
            delete ptr;
    }
    

    ändere in:

    int main() { // kein überflüssiges void
        auto ptr = new child(); // *new ist praktisch immer falsch!
        ptr->A(2,3);
        delete ptr;
    }
    

    Noch besser wäre der Einsatz von Smart-Pointern:

    int main() {
        auto ptr = std::make_unique<child>();
        ptr->A(2,3);
        // automatisches cleanup
    }
    


  • Okay danke für die Anmerkungen, habe was Sinnvoll ist jetzt ausgebessert.
    Dachte der Typecast wäre schief gegangen. Durch das Überladen wurde die A(..) bzw. Init Methode als neue Methode erkannt nicht als eine die überschrieben werden soll.


Anmelden zum Antworten