was ist besser: mit new oder ohne?

  • Hi!

    Nehmen wir an ich habe eine Class namens Task. Was ist vernünftiger:

    Task cTask;
    int nResult;

    nResult = cTask.Run();
    return nResult;

    -- oder --

    Task *pTask = new Task;
    int nResult;

    pTask = new Task;
    nResult = pTask->Run();
    delete pTask;

    return nResult;

    Wo liegen bei diesen beiden die feinen Unterschiede?

  • Ich weiß leider nicht, um (und ob) welche Klassenbibliothek es sich hier handelt.

    Aber mal ganz allgemein:

    Die erste Variante legt die Variable auf dem Stack ab, die zweite alloziert Speicher aus dem Freispeicher (Heap).

    Tendenziell ist es für größere Objekte empfehlenswert, diese im Heap anzulegen, da der Speicherplatz im Stack sonst knapp werden könnte.

    Eine "bessere" Variante in dem Sinn gibt es also nicht, es kommt ganz auf die Situation an.

    Beachte auch, dass Objekte, die im Heap gespeichert sind, explizit wieder freigegeben werden müssen (mittels delete).

    Objekte, die im Stack angelegt sind, haben (so sie nicht static deklariert werden) ihr Leben hingegen am Ende des Codeblocks verwirkt ;)

    Je nach Klassenbibliothek gibt es aber auch Vorschriften (zB VCL) oder Empfehlungen, wie neue Objekte instanziiert werden sollten.

    HTH,

    Jeremy

    Eins Zwei Gras Bär Hund Vier Muh Macht Die Kuh

  • Hi Jeremy!

    Klingt einleuchtend :)
    (Keine Klassenbibliothek)

    Und wo du dich so toll auskennst, hab ich gleich noch eine Frage. Und zwar im Task selbst drin. Entweder so:

    //----------------------------------------
    // CLASS
    //----------------------------------------

    class Task
    {
    public:
    Task();
    ~Task();

    private:
    static void Change(int nZahl);
    int nNumber;
    };

    //----------------------------------------
    // GLOBAL
    //----------------------------------------

    Task *pTask = NULL;

    //----------------------------------------
    // Task::Task
    //----------------------------------------

    Task::Task()
    {
    pTask = this;
    }

    //----------------------------------------
    // Task::Change
    //----------------------------------------

    void Task::Change(int nZahl)
    {
    pTask->nNumber = nZahl;
    }


    == oder ==

    //----------------------------------------
    // CLASS
    //----------------------------------------

    class Task
    {
    public:
    Task();
    ~Task();
    void Change(int nZahl);

    private:
    int nNumber;
    };

    //----------------------------------------
    // IMPLEMENTATION
    //----------------------------------------

    void Change(nZahl);

    //----------------------------------------
    // GLOBAL
    //----------------------------------------

    Task *pTask = NULL;

    //----------------------------------------
    // Task::Task
    //----------------------------------------

    Task::Task()
    {
    pTask = this;
    }

    //----------------------------------------
    // Task::Change
    //----------------------------------------

    void Task::Change(int nZahl)
    {
    nNumber = nZahl;
    }

    //----------------------------------------
    // Change
    //----------------------------------------

    void Change(int nZahl)
    {
    pTask->Change(nZahl);
    }


    (Ich hoff da stecken jetzt keine Fehler drin)
    Also ums aufs Wesentliche zu bringen: was bewirkt das von dir bereits angesprochene Wörtchen static im private bereich? Irgendwelche Vor- oder Nachteile oder eventuell tut-man-nicht-Programmierstile?
    Was ist also vernünftiger von diesen beiden Varianten?

    Ich hoffe du kannst mir auch hierbei helfen :)

    David

  • Folgendes:

    Mir ist nicht ganz klar, wozu der globale Zeiger pTask gut sein soll ... Falls du sicherstellen willst, dass nur genau eine Instanz der Klasse erstellt wird, rate ich Dir, mal in Google nach "Singleton Pattern" zu suchen.

    Um zu beantworten, was static tut:
    Dieses Schlüsselwort ist ziemlich vielfältig. So, wie Du es eingesetzt hast, bewirkt es, dass eine Methode, auf die der static Modifier angewendet wird, nicht auf einer Instanz der Klasse angewendet werden kann, sondern quasi nur einmal, nämlich für die Klasse selbst, existiert. Man kann sie dann so aufrufen:
    Klasse:statischeMethode();
    aber nicht:
    Klasse a;
    a.statischeMethode();

    Wiederum eine andere Bedeutung hat static im Rumpf einer Funktion. Dort bedeutet es, dass eine mit static deklarierte Variable sozusagen einen "Memory-Effekt" hat, dh, beim nächsten Aufruf der Funktion hat die Variable noch den Wert, den sie beim letzten Aufruf der Funktion zugewiesen bekam.

    Bsp.:

    void doSomething()
    {
    static int a = 15;
    std::cout << a << std::endl;
    a *= 2;
    }

    doSomething();
    > 15
    doSomething();
    > 30

    usw.

    Welche Variante jetzt konkret besser ist, kann ich Dir leider nicht sagen, für mich wirken beide etwas seltsam. Falls Du genauer spezifizieren kannst, was Du machen willst, können wir Dir sicher weiterhelfen.

    Eins Zwei Gras Bär Hund Vier Muh Macht Die Kuh

  • aufruf lautet
    Klasse::statischeMethode();

    lg
    ines

    :catwoman: der unterschied zw. reifen & politikern ist, daß reifen ein mindestprofil brauchen.

  • Zitat

    Original geschrieben von catwoman

    aufruf lautet
    Klasse::
    statischeMethode();

    lg
    ines

    Das ist natürlich richtig, hab mich vertippt :)

    Danke.

    Eins Zwei Gras Bär Hund Vier Muh Macht Die Kuh

Jetzt mitmachen!

Sie haben noch kein Benutzerkonto auf unserer Seite? Registrieren Sie sich kostenlos und nehmen Sie an unserer Community teil!