Polymorphie und Referenzen



  • Ich spiele gerade ein wenig mit Referenzen und Vererbung herum.
    Was ich gerne hätte, wäre eine Referenz auf ein Basis-Klassen-Objekt, das abhängig vom tatsächlichen Typ die "richtige" Funktion aufruft:

    #include <iostream>
    
    using namespace std;
    
    class Base
    {
    public:
      virtual void operator()()
      {
        cout << "Base Class" << endl;
      }
    
      virtual ~Base() {};
    };
    
    class Derived : public Base
    {
    public:
      void operator()()
      {
        cout << "Derived Class" << endl;
      }
    };
    
    int main()
    {
    
      Base b;
      Derived d;
    
      Base & ref = d;
      ref();
    
      ref = b;
      ref();  
    
      return 0;
    }
    

    Dieser Code scheint nicht zu tun, was ich möchte. Ich bekomme zweimal die Ausgabe "Derived Class".

    Was müsste ich ändern, um einmal den Operator der abgeleiteten und einmal der Basisklasse über meine Referenz aufzurufen?

    Ich würde, wenn möglich, gerne die Verwendung von Zeigern vermeiden.


  • Mod

    ref = b;
    

    Bist du dir im Klaren darüber, was diese Zuweisung tut?



  • int main()
    {
    
      Base b;
      Derived d;
    
      Base & ref = d;
      ref();
    
      Base& ref2 = b;
      ref2();  
    }
    


  • @camper:

    Natürlich bin ich mir NICHT ganz im Klaren darüber, was ich tue. Ansonsten würde das Problem ja nicht entstehen.

    Eine Erklärung des Sachverhalts oder ein Literaturhinweis wären hilfreich.
    So wie ich die Sache bisher deute, ist es so, dass eine Referenz ein Alias für ein vorhandenes Objekt ist, das nicht mehr geändert werden kann.
    Eventuell gibt es eine Lösung mit reference_wrapper?
    An dieser STelle bin ich leider zu unerfahren um eine gute Lösung zu finden, weshalb ich hier im Forum anfrage.



  • shisha schrieb:

    Ich würde, wenn möglich, gerne die Verwendung von Zeigern vermeiden.

    Dies ist aber ein Fall, wo ich einen Zeiger benutzen würde, sofern denn diese Variable wirklich wiederverwendet werden muss. (ansonsten siehe manni66s Lösung)

    Ohne sichtbaren Pointer geht es auch:

    Base b;
      Derived d;
    
      auto ref = std::ref<Base>(d);
      ref();
    
      ref = std::ref(b);
      ref();
    

    Aber im Prinzip versteckt das den Zeiger auch nur und wird z.B. gerne benutzt, wenn Referenzen irgendwie durchgereicht werden müssen, z.B. an einen Thread oder so - würde ich hier nicht benutzen. Aber zumindest wäre die Aufgabenstellung "ohne Zeiger" hiermit erfüllt 😉

    Mit deinem ref=b rufst du operator= des Ref-Objekts mit dem Parameter b auf. Wie könntest du sonst den Inhalt des refezenzierten Objekts ändern?


Anmelden zum Antworten