Klassen durch Array ansprechen



  • Hallo,

    wisst ihr wie ich z.B. die Klassen:

    class spieler_1{
     public:
       int function();
    };
    class spieler_2{
     public:
       int function();
    };
    class spieler_3{
     public:
       int function();
    };
    class spieler_4{
     public: 
       int function();
    }
    

    durch ein Array ansprechen kann?

    Hab mir das ungefähr so vorgestellt:

    int main(){
       ...Klassen F[4];
       spieler_1 F[1];
       spieler_2 F[2];
       spieler_3 F[3];
       spieler_4 F[4];
    

    mein Ziel ist es, die Klassen-Funktionen ungefähr so aufrufen zu können:

    for( int i=0; i<4; i++) {
          F[i].function();
          }
    

    Habe schon viel "rumexperimentiert", kriege es aber (auch mithilfe von google) nicht hin 😞

    Falls mir jemand helfen könnte, würde ich mich freuen 😋



  • Du hast einen falschen Ansatz. Ich sehe zwei Interpretationsmöglichkeiten:

    1.) Du willst 4 Spieler erstellen, die vom gleichen Typ sind. Dafür brauchst du eine Klasse und 4 Instanzen.

    class Spieler
    {
    
    };
    
    // ---
    Spieler F[4];
    

    2.) Du benötigst tatsächlich 4 Klassen. Damit diese zueinander kompatibel sind, kannst du eine gemeinsame Basisklasse festlegen. Je nachdem brauchst du auch Polymorphie (wenn du die Klassen in einem Array speichern willst, oder genauer Zeiger auf deren Instanzen).

    Das zweite Vorgehen lohnt sich wirklich nur, wenn die Spieler sich massgeblich in der Funktionalität unterscheiden. Falls nur mehrere Spieler vom gleichen Typ benötigt werden, ist 1.) besser.



  • Hy, danke für deine Antwort

    was ich konkret umsetzen will, ist, dass
    ich ein Spiel aufbaue, welches verschiedene Spielfiguren
    mit versch. Funktionen hat.

    Um einen mögliche Zug zu überprüfen will ich nicht jede
    einzele Funktion einer Figuren Klasse aufrufen sonder
    in einer Schleife alle Figuren, die die selbe Basisklasse haben,
    aber unterschiedliche Funtionen, auzurufen.

    anstatt

    Figur_1.function(...)
    Figur_2.function(...)
    Figur_3.function(...)
    

    möchte ich

    Figur[i].function(...)

    schreiben können

    gruss tillt



  • Wie gesagt wäre das mit Polymorphie lösbar. Allerdings bin ich weiterhin kritisch gegen dein Vorgehen eingestellt: Existiert denn von jeder Spielfigur nur eine Instanz? Wenn es mehrere gäbe, lohnen sich Container. Dann kannst du die einzelnen Instanzen nämlich auch spezifisch ansprechen. Nur aus Bequemlichkeit oder Code-Ersparnis würde ich hier keine Schleife oder gemeinsame Typen machen.

    Falls du nicht dieser Ansicht bist, kannst du dich beispielsweise hier über Vererbung und nachfolgend über virtuelle Methoden (sozusagen der Kern der dynamischen Polymorphie) erkundigen.



  • Am besten poste ich mal den Code:

    #include <iostream>
    #include <string>
    
    using namespace std;
    
    class Figur{
          public:
            int    Koordinaten[2],    wert,       state;	// [1]:x, [2]:y
            bool   color;
            string name;
            bool   init( int _Koordinaten[2], int _wert, bool _state, bool _color,  string _name);  //      Initalisierung
          };
    
    class	Turm:	Figur{
          public:
    		bool	Zug( int nummer,  int vonKoordinaten[2], int nachKoordinaten[2]);
    };
    class	Springer:	Figur{
    	  public:
    		bool	Zug( int nummer,  int vonKoordinaten[2], int nachKoordinaten[2]);
    };
    class	Laeufer:	Figur{
    	public:
    		bool	Zug( int nummer,  int vonKoordinaten[2], int nachKoordinaten[2]);
    };
    class	Koenig:	Figur{
    public:
    		bool	Zug( int nummer,  int vonKoordinaten[2], int nachKoordinaten[2]);
    };		
    class	Dame:	Figur{
    public:
    		bool	Zug( int nummer,  int vonKoordinaten[2], int nachKoordinaten[2]);
    };
    class	Bauer:	Figur{
    public:
    		bool	Zug( int nummer,  int vonKoordinaten[2], int nachKoordinaten[2]);
    };
    
    bool Turm::Zug( int nummer,  int vonKoordinaten[2], int nachKoordinaten[2])	{
      };
    bool Springer::Zug( int nummer, int vonKoordinaten[2], int nachKoordinaten[2])	{
    	return true;
      };
    bool Laeufer::Zug( int nummer, int vonKoordinaten[2], int nachKoordinaten[2])	{
      return true;
      };
    bool Koenig::Zug( int nummer, int vonKoordinaten[2], int nachKoordinaten[2])	{
      return true;
      };
    bool Dame::Zug( int nummer, int vonKoordinaten[2], int nachKoordinaten[2])	{
      return true;
      };
    bool Bauer::Zug( int nummer, int vonKoordinaten[2], int nachKoordinaten[2])	{
      return true;
      };
    
    int	main()	{
    
    	Turm	F[1];
    	Springer F[2];
    	....
    
    	system("PAUSE");
    
    	return	true;
    
    	}
    

    -> Bin noch ein relativer newbie, tut mir leid, wenn meine Frage blöd ist.
    Die "Figuren" haben jeweils unterschiedliche Zugfunktionen.



  • tillt schrieb:

    -> Bin noch ein relativer newbie, tut mir leid, wenn meine Frage blöd ist.

    Mach dir deswegen keine Gedanken. Deine Frage ist durchaus berechtigt! 🙂

    Grundsätzlich kann sich bei Klassen, deren relativ ähnlich sind, aber vom Verhalten her nicht ganz identisch, auch eine Fallunterscheidungs-Variable anbringen. Das zahlt sich besonders bei vielen einzelnen Fällen und kleinen Abweichungen aus. Dafür gibt es enum und per switch kann man leicht spezifisch handeln.

    class MyClass
    {
        public:
            enum Type
            {
                First,
                Second,
                Third,
            };
    
        private:
            Type MyType;
    };
    

    Aber bei dir mit den Schachfiguren könnte sich Vererbung auch lohnen. In der Basisklasse müsstest du eine (rein) virtuelle Methode bereitstellen, die in den abgeleiteten Klassen überschrieben wird.

    class Figur
    {
         public:
            virtual bool Zug(int nummer,  int vonKoordinaten[2], int nachKoordinaten[2]) = 0;
    };
    

    Diese virtuelle Methode implementierst du hier nicht (deshalb rein virtuell, das "= 0" bei der Deklaration), sondern erst in den abgeleiteten Klassen. In der main() -Funktion würde dann etwa Folgendes stehen:

    int main()
    {
        // Array aus Zeigern auf Basisklasse erstellen. X = Anzahl Figuren
        // Die Zeigern zeigen aber auf abgeleitete Klassen.
        Figur* Array[X] = {new Turm(..), new Turm(..), new Koenig(..), ...};
    
        // Die Königs-spezifische Zug-Memberfunktion aufrufen
        Array[2]->Zug(...);
    }
    

    Natürlich etwas sauberer und in besserem Kontext. Und an die delete s denken. Vielleicht seien hier auch noch gerade die STL-Container erwähnt, die sich viel komfortabler und sicherer als Arrays handhaben lassen. Schau dazu mal in den FAQ dieses Unterforums nach STL.



  • Hy, ....war schon schlafen 🙄

    Vielen Dank für deine Hilfe ich denke jetzt krige ich es hin! 👍

    ...werd mir gleich mal die FAQ zur STL durchlesen

    schönen Tag noch Till



  • Ah sorry, ich hab dich falsch informiert. Die STL stehen nicht in den FAQ, sondern in den Artikeln. Dafür hab ich dir hier gleich die Links:

    1) Container
    2) Iteratoren und Algorithmen
    3) Hilfsklassen und Erweiterungen



  • ...schon gefunden, aber danke


Anmelden zum Antworten