Initialisiererliste



  • aus einem Forum kopiert/geklaut..wie man das auch sagt 😉



  • So:

    struct Klasse
    {
      private:
        int Zahl1, Zahl2, Zahl3;
      public:
        Klasse(int Zahl1, Zahl2, Zahl3)
        {
          this->Zahl1 = Zahl1;
          this->Zahl2 = Zahl2;
          this->Zahl3 = Zahl3;
        }
    };
    


  • Nur mal grob hingeworfen:
    mit Zuweisungen:

    C1(int value)
    {
      zahl1 = value; //hier könntest du auch this->zahl1 schreiben, ist aber nicht notwendig
      zahl2 = 2*value;
      zahl3 = 1;
    }
    

    mit Initialisierungsliste:

    c1(int value)
     : zahl1(value)
     , zahl2(2*value)
     , zahl3(0)
    {}
    

    Bei int-Werten macht es keinen großen Unterschied, weil deren Default-Konstruktor nicht wirklich viel zu tun hat - und jeder vernünftige Compiler den Code optimieren kann. Problematisch wird es, wenn du dort mit Klassen arbeitest, die nicht-triviale Konstruktoren haben.

    Edit: Pointer-Zuriff korrigiert 😃



  • Man kann ja auch so gut auf die Member einer Klasse über einen Zeiger mit dem . -Operaror zugreiffen 😉 .



  • EOutOfResources schrieb:

    Man kann ja auch so gut auf die Member einer Klasse über einen Zeiger mit dem . -Operaror zugreiffen 😉 .

    War wohl nur n Tippfehler, passiert dir sicherlich oft genug 🙄



  • Ja, besten Dank nochmal. Hat mir wirklich weiter geholfen.



  • Ich habe zu diesem Thema auch eine Frage. Benutzt man die Initialisierungsliste nun nur für "primitive" Datentypen wie bool, double, int usw. oder sollte man wirklich alle Member einer Klasse in die Liste schreiben? Macht es also Sinn z.B. den std::wstring-Member einer Klasse in die Initialisierungsliste zu schreiben?
    Wenn ja mit welchem Wert sollte man diesen Member initialisieren?

    class MyClass
    {
    public:
    MyClass() :
    myString() // oder
    //myString(0) // oder
    //myString(L"")
    {
    }
    
    private:
    std::wstring myString;
    };
    

    Das wird dem Compiler wahrscheinlich egal sein, aber welche Variante ist optisch vorzuziehen?



  • Wenn du den Default-Konstruktor aufrufen möchtest, brauchst du gar nichts tun.



  • Achso, der wird dann also automatisch aufgerufen.
    Eine letzte Frage noch. Warum verwendet man bei structs ZeroMemory?
    Z.B. hier:

    WNDCLASSEX wcex;
    	ZeroMemory(&wcex, sizeof(WNDCLASSEX));
    

    Haben Strukturen keine Initialisierungsliste?



  • bzw. wird hier nicht der Default-Constructor aufgerufen?



  • Das ist C-Code. Vergiss das ganz schnell.



  • Initliste schrieb:

    Achso, der wird dann also automatisch aufgerufen.
    Eine letzte Frage noch. Warum verwendet man bei structs ZeroMemory?
    Z.B. hier:

    WNDCLASSEX wcex;
    	ZeroMemory(&wcex, sizeof(WNDCLASSEX));
    

    Haben Strukturen keine Initialisierungsliste?

    Structs haben keinen Konstruktor, den man aufrufen könnte. Und selbst unter C würde ich lieber die direkte Methode WNDCLASSEX wcex = {0}; verwenden.



  • Initliste schrieb:

    Warum verwendet man bei structs ZeroMemory?

    Wo auch immer Du das her hast; Du schließt aus einem speziellen Fall auf allgemeines.

    'Man' verwendet nicht ZeroMemory() bei structs.

    Jemand hat's in Deinem zitierten Fall getan.

    Himmelweiter Unterschied!



  • CStoll schrieb:

    Structs haben keinen Konstruktor, den man aufrufen könnte.

    Structs können in C++ einen Konstruktor haben, in C natürlich nicht 🙂

    CStoll schrieb:

    Und selbst unter C würde ich lieber die direkte Methode WNDCLASSEX wcex = {0}; verwenden.

    👍



  • Meinst du nur das ZeroMemory? Die WNDCLASSEX brauche ich um mir ein Win32-Fenster zu erzeugen?



  • Geht der folgende Code so in Ordnung?

    ATOM MyRegisterClassEx()
    {
    	WNDCLASSEX wcex;
    	wcex.cbSize = sizeof(WNDCLASSEX);
    	wcex.style = CS_HREDRAW | CS_VREDRAW | CS_OWNDC;
    	wcex.lpfnWndProc = static_cast<WNDPROC>(WndProc);
    	wcex.cbClsExtra = 0;
    	wcex.cbWndExtra = sizeof(LONG_PTR);
    	wcex.hInstance = hInstance;
    	wcex.hIcon = hIcon;
    	wcex.hCursor = LoadCursor(NULL, IDC_ARROW);
    	wcex.hbrBackground = NULL;
    	wcex.lpszMenuName = NULL;
    	wcex.lpszClassName = L"MyClass";
    	wcex.hIconSm = NULL;
    	return RegisterClassEx(&wcex);
    }
    


  • Also ich wäre ja für eine WNDCLASSEX Factory mit Style Policies ala Alexandrescu 😃


  • Mod

    CStoll schrieb:

    Structs haben keinen Konstruktor, den man aufrufen könnte.

    structs sind Klassen. Alle Klassen verfügen über einer Kopierkonstruktor und, falls kein Konstruktor explizit deklariert wurde, auch über einen Defaultkonstruktor.

    In C++0x sind die Regeln etwas komplizierter.



  • Bjarne Stroustrup schreibt in seinem Buch Die C++ Programmiersprache wie folgt

    struct s { /* .... */ }
    // ist ein Synonym für
    class s { public: /* ... */}
    

    @Initliste

    Es macht auf jeden Fall Sinn, eine Struktur wie WNDCLASSEX , vorher mit ={0} oder ZeroMemory bzw. memset abzunullen.
    Nach einem

    WNDCLASSEX wcex;
    

    steht nämlich zunächst Schrott in der Struktur drin. Vergisst man beim Initialisieren ein Member -> 😮


Anmelden zum Antworten