Singleton Pattern



  • static



  • meinst du wenn ich dann in meiner Main das Objekt "rs" von der Klasse "dieRessourcen" wie folgt erzeuge, kann ich von allen anderen darauf zu greifen?

    static dieRessourcen rs(Gold, Stein, Getreide, Holz, Haeuser, Bewohner);
    

    Ist somit rs von überall verwendbar?



  • nein
    du musst jeden Wert der Klasse static machen,dann existiert sie Klasse sogar, ohne dass du sie initialisierst



  • sorry, irgendwie klappts nicht... und ich weiß auch nicht ganz wie du das meinst... soll ich die klasse "dieRessourcen" wie folgt schreiben:

    #ifndef _DIERESSOURCEN_H_
    #define _DIERESSOURCEN_H_
    
    #include <ressourcen.h>
    
    class dieRessourcen
    
    {
    private:
    		static Ressourcen Gold; 
    		static Ressourcen Stein;
    		static Ressourcen Getreide;
    		static Ressourcen Holz;
    		static Ressourcen Haeuser;
    		static Ressourcen Bewohner;
    		//class Gui *m_Gui; 
    
            friend class Menu;
    		friend class Gui;
    public:
    
    	dieRessourcen(const Ressourcen &myGold, const Ressourcen &myStein, const Ressourcen &myGetreide, 
    		const Ressourcen &myHolz, const Ressourcen &myHaeuser, const Ressourcen &myBewohner) {
    		Gold = myGold;
    		Stein = myStein;
    		Getreide = myGetreide;
    		Holz = myHolz;
    		Haeuser = myHaeuser;
    		Bewohner = myBewohner;
    	}
    
    	//void SetKlasse_Gui(class Gui *myGui); 
    
    };
    
    #endif
    

    ??



  • jep,aber du musst in eine passende cpp datei noch startwerte für die Werte schreiben, wie zb:
    dieRessourcen::Gold=beliebiger_wert;



  • Ich glaub du hast das Prinzip wie so ein Singleton aufgebaut ist noch nicht richtig verstanden.

    1.) Zuerst definierst du "dieRessourcen" so wie du sie später benötigst. Ganz wie eine normale Klasse, d.h. public funtions und private members.

    2.) Dann entfernst du alle Konstrukturen der Klasse. Vorsicht, wenn du selbst keine definiert hast fügt der Compiler sie selbst hinzu. In diesem Fall schreibst du den Konstruktur einfach selbst und machst ihn private.

    3.) Nach den beiden ersten Schritten hast du eine ganz normale Klasse die nicht zu verwenden ist, weil keine Instanz von ihr erstellt werden kann, weil keine Konstruktoren aufgerufen werden können. Aus diesem Grund...

    4.) Füge zu deiner Klasse eine statische Funktion getInstance() hinzu. Diese Funktion erzeugt beim ersten Auruf eine Instanz von sich selbst und liefert sie dem Aufrufer zurück. Ausserdem speichert die Funktion diese Instanz als static private member ab. Alle nachfolgenden Aufrufe von getInstance() liefern immer wieder genau dieses eine member an den Aufrufer zurück. Daraus folgt...

    5.) Alle "Anwendungen" arbeiten mit ein und derselben Instanz deiner KLasse.

    Das war jetzt die 08/15 Methode. Zu diesem Thema gibt es noch einiges an Feinheiten die du bei Interesse nachlesen kannst.

    mfg JJ



  • so mal sehen ob ich es jetzt richtig verstanden habe:

    ich habe meine Main:

    #include <iostream>
    using namespace std;
    
    #include <menu.h>
    #include <ressourcen.h>
    #include <dieressourcen.h>
    #include <gui.h>
    
    int main() {
    
    	Gui Spielfeld("Spielfeld");
    
    	Spielfeld.showFrames();
    
             //hier erzeuge ich die Startwerte
    	Ressourcen Gold(gold, 1, 1000, 0); 
    	Ressourcen Stein(stein,  1, 1000, 0);
    	Ressourcen Getreide(getreide, 5, 1000, 0);
    	Ressourcen Holz(holz, 1, 1000, 0);
    	Ressourcen Haeuser(haeuser, 1);
    	Ressourcen Bewohner(bewohner, 100);
    
             //und hier übergebe ich die Startwerte dem Konstruktor
    	dieRessourcen rs(Gold, Stein, Getreide, Holz, Haeuser, Bewohner);
    
    	Spielfeld.spielstatusfeldAnzeigen(rs);
    
    	Menu Auswahlmenu("Auswahlmenu", hauptmenu);
    
    	Auswahlmenu.imHauptmenu(Spielfeld, rs);
    
    	return 0;
    
    }
    

    und so sieht meine dieressourcen.cpp aus:

    #include <dieressourcen.h>
    
    dieRessourcen::dieRessourcen(const Ressourcen &myGold, const Ressourcen &myStein, const Ressourcen &myGetreide, 
    	const Ressourcen &myHolz, const Ressourcen &myHaeuser, const Ressourcen &myBewohner) {
             //Füllt die oben übergeben Werte ein (Das war das mit den Startwerte, was du gemeint hast, oder?
    	Gold = myGold;
    	Stein = myStein;
    	Getreide = myGetreide;
    	Holz = myHolz;
    	Haeuser = myHaeuser;
    	Bewohner = myBewohner;
    
    }
    

    und meine dieressourcen.h sieht wie folgt aus:

    #ifndef _DIERESSOURCEN_H_
    #define _DIERESSOURCEN_H_
    
    #include <ressourcen.h>
    
    class dieRessourcen
    
    {
    private:
    		static Ressourcen Gold; 
    		static Ressourcen Stein;
    		static Ressourcen Getreide;
    		static Ressourcen Holz;
    		static Ressourcen Haeuser;
    		static Ressourcen Bewohner;
    		//class Gui *m_Gui; 
    
            friend class Menu;
    		friend class Gui;
    public:
    
    	dieRessourcen(const Ressourcen&, const Ressourcen&, const Ressourcen&, 
    		const Ressourcen&, const Ressourcen&, const Ressourcen&);
    
    };
    
    #endif
    

    und wie kann ich jetzt z. B. aus der Datei menu.cpp auf rs (objekt von dieressourcen) zugreifen? wenn ich dort z. B. rs.Gold.kaufen() mache, sagt er "error C2065: 'rs' : nichtdeklarierter Bezeichner" ?? irgendwo hab ich scheinbar wsa noch nicht ganz verstanden 🙂

    aber vielen dank schon mal für die Hilfe!! An dem blöden Problem häng ich schon seit 2 wochen und mein Prof. meinte nur so "Singleton Pattern"..



  • @John Doe: Danke für deine Hilfe, hab den Beitrag eben erst gesehen. Nach deiner Schritt für Schritt erklärung klingt es gar nicht mal so schwer... ich versuchs jetzt nebenbei auch noch mal mit dem Pattern 🙂



  • nein ganz falsch
    resourcen.h:

    #include <ressourcen.h>
    
    class dieRessourcen
    
    {
    private:
            static Ressourcen Gold; 
            static Ressourcen Stein;
            static Ressourcen Getreide;
            static Ressourcen Holz;
            static Ressourcen Haeuser;
            static Ressourcen Bewohner;
            //class Gui *m_Gui; 
    
            friend class Menu;
            friend class Gui;
    public:
    
            void setSteine(int Anzahl);
    
    };
    

    resourcen.cpp

    dieRessourcen::Gold=1000;//da ich nich weis wie resourcen aufgebaut sind nehm ichs einfach mal als int wert^^
        dieRessourcen::Stein=1000;
        dieRessourcen::Getreide=100;
        //usw
    

    das hat mit dem constructor garnichts mehr zu tun, der wird soweit ich weis garnicht ausgeführt.
    wenn du zb ne funktion void setStein(int anzahl); hast,dann kannst du so auf sie zugreifen:
    dieRessourcen::setStein(179);

    btw: sowas steht in jedem halbwegs anständigen Buch^^
    hier noch ein link zur FAQ http://www.c-plusplus.net/forum/viewtopic.php?t=39471



  • otze schrieb:

    nein ganz falsch

    Ah, und wie garantierst du, dass alle Member initialisiert werden? (und zwar nicht mit den default werten.



  • er wollte ne alternative zu singleton ich geb ihm eine alternative zu singleton 🙄

    desweiteren gibts auchs chöne methoden mit denen man member verändern kann, bei static klassen gehts aufjedenfall nicht mit dem ctor



  • otze schrieb:

    er wollte ne alternative zu singleton ich geb ihm eine alternative zu singleton 🙄

    Er hat ja Singleton noch nichteinmal richtig implementiert...
    Und wo steht, dass er eine alternative sucht?

    @OP:
    machs in etwa so:

    class dieResourcen
    {
    friend class Singleton;
    private:
      ~dieResourcen(){}
    public:
    /*whatever*/
    };
    
    class Singleton
    {
    public:
      static dieResourcen& instance()
      {
        static dieResourcen instance;
        return instance;
      }
    };
    

    Dann kannst du
    dieResourcen& res=Singleton::instance();
    res.getGold();
    oder aehnliches machen.



  • Shade Of Mine schrieb:

    otze schrieb:

    er wollte ne alternative zu singleton ich geb ihm eine alternative zu singleton 🙄

    Er hat ja Singleton noch nichteinmal richtig implementiert...
    Und wo steht, dass er eine alternative sucht?

    hmm in etwa hier:

    Es geht eigentlich nur darum die Klasse dieRessourcen global zu machen? 
    
    Vielleihct hat ja von euch noch jemand einen anderen trick, der weniger kompilziert ist :-)
    


  • @shade:
    deine version vom singleton funzt fast bei mir. Also in mein main.cpp geht es, wenn ich allerdings dann auf das erzeuget objekt "res" in meiner gui.cpp zugreifen will, bekomme ich immer "nicht deklarierter bezeichner". und wenn ich dann in der gui.cpp den aufruf über "dierourcen& res = Singleton::instance()" mache (vorher natürlich in der main raus), bekomme ich einen "INTERNAL COMPILE ERROR" :-//

    irgenwdo scheint noch was falsch zu sein...

    danke nochmal für alle dir mir geholfen haben!! hab das singleton zumindest jetzt besser verstanden..


Anmelden zum Antworten