Einen Array von C++ Objekten mit Argumenten erstellen



  • Wozu brauchst du STRINGMAX? Wie lang darf dein String damit jemals werden? Hält dein Programm sich datan?


  • Mod

    Cheerful Coder schrieb:

    Vielen Dank für die Hilfe!
    Habs jetzt soweit fast fertig. 😉 Er gibt nur noch nen Fehler

    Beim Überfliegen fallen mir in fast jeder Funktion Fehler auf (Default-konstruktor und Destruktor sind die Einzigen ohne Fehler - wobei dein Defaultkonstuktor ggf. trotzdem überarbeitet werden sollte). C-String-Funktionen reagieren in der Regel allergisch auf Nullpointer. Wozu ist eigentlich count gut?



  • manni66 schrieb:

    Wozu brauchst du STRINGMAX? Wie lang darf dein String damit jemals werden? Hält dein Programm sich datan?

    Ich hab es so übernommen aus dem Buch ... dachte das das so möglich wäre,
    wenn ich es als statisch in der Klasse deklariere...ist das falsch? 😕

    camper schrieb:

    Beim Überfliegen fallen mir in fast jeder Funktion Fehler auf (Default-konstruktor und Destruktor sind die Einzigen ohne Fehler - wobei dein Defaultkonstuktor ggf. trotzdem überarbeitet werden sollte). C-String-Funktionen reagieren in der Regel allergisch auf Nullpointer. Wozu ist eigentlich count gut?

    Count soll abzählen wieviele Buchstaben in stringup bzw. stringlow groß- bzw. kleingeschrieben werden sollen, aber vermutlich kann ich auch sowas nehmen wie

    while (*sentence)
    

    richtig? 🙂

    Könnteste mir vielleicht sagen, was meine Fehler sind? 🙂 Reicht auch
    wenns die gröbsten Fehler sind, das wäre sehr hilfreich! 😉


  • Mod

    Es ist möglich mit einem Nullzeiger einen leeren String darzustellen. Das ist allerdings inkompatibel mit den meisten FUnktionen der Standardbibliothek, konsequenterweise müsste bei jedem Funktionsaufruf (strlen,strcpy was auch immer) vorher dieser Fall geprüft werden.
    Damit sind nahezu alle Funktionen falsch.

    Praktisch ist die Variante mit Nullzeiger allerdings nicht.
    Eine Möglichkeit besteht darin, den leeren String nicht als Sonderfall zu betrachten - dann verzichtet man z.B. gleich auf einen eigenständigen Defaultkonstruktor und verpasst z.B. dem const char*-Konstruktor ein Defaultargument.

    String(const char* s="")
    {
        std::size_t len = strlen(s);
        sentence = new char[len + 1];
        std::memcpy( sentence, s, len + 1 );
    }
    

    Eine andere Möglichkeit besteht darin, dafür ein statisches Array zu verwenden:

    class String
    {
    private:
        static char empty_string[1];
    ...
    };
    
    char String::empty_string[1] = { '\0' };
    
    String::String()
    {
        sentence = empty_string;
    }
    
    String::~String()
    {
        if ( sentence != empty_string )
            delete [] sentence;
    }
    

    Von der Beschränkung auf STRINGMAX Zeichen ist nichts zu halten. Man könnte dafür ja gleich das Array als Klassenmember halten und auf dynamische Speicherverwaltung verzichten. In jedem Fall ist bei einem der Länge nach begrenzten String sicherzustellen, dass diese Grenze nicht überschritten wird. Das ist z.B. in String::String(const char *str) nicht der Fall.
    Der operator+ ist seltsam; normalerweise sollte dieser nicht seine Argumente verändern. Zudem besteht dann auch ein Aliasproblem:

    str s = "foo";
    s+s;
    

    dürfte nicht funktionieren. Der Test auf Länge fehlt sowieso. Der andere operator+ funktioniert auch nicht.



  • Ich hab es so übernommen aus dem Buch ... dachte das das so möglich wäre,
    wenn ich es als statisch in der Klasse deklariere...ist das falsch?

    Nicht direkt, STRINGMAX darf halt nur so groß werden, wie der Index es werden darf.

    Eine Möglichkeit besteht darin, den leeren String nicht als Sonderfall zu betrachten - dann verzichtet man z.B. gleich auf einen eigenständigen Defaultkonstruktor und verpasst z.B. dem const char*-Konstruktor ein Defaultargument.

    Ein leerer String hat die Länge 1 und besteht nur aus '\0' , das sollte auch die C-Funktionen nicht verstören.

    Von der Beschränkung auf STRINGMAX Zeichen ist nichts zu halten. Man könnte dafür ja gleich das Array als Klassenmember halten und auf dynamische Speicherverwaltung verzichten.

    Nicht direkt, STRINGMAX sollte die größtmögliche Zahl des Indexes vorgeben.

    Warum reservierst du - immer, wenn du temporären Speicher reservierst nicht strlen() viele Elemente, anstatt STRINGMAX? Ist doch pure Speicherverschwendung.

    Abgesehen davon kopiert strcpy den abschließenden '\0' Terminierer nicht mit, den musst du meines Wissens selbst anhängen.

    Übrigens... Welches Buch liest du denn?



  • Der Tobi schrieb:

    Ein leerer String hat die Länge 1 und besteht nur aus '\0'

    Ein leerer String hat die Länge Null.



  • Sone schrieb:

    Der Tobi schrieb:

    Ein leerer String hat die Länge 1

    Hast du nen Hirnschaden? ^^

    Anscheinend hast du einen Hirnschaden, wenn du gleich drauf los musst.



  • [Rewind] schrieb:

    Anscheinend hast du einen Hirnschaden, wenn du gleich drauf los musst.

    Gut, das war sehr grob, tut mir Leid.


  • Mod

    *facepalm*



  • camper schrieb:

    *facepalm*

    Ach, Scheiße! Ich hab's falsch verstanden. Natürlich hat camper Recht. Ich dachte er meint leere Strings (also einen Zeiger auf das Terminierungszeichen)... weil ich schon wieder zu schnell lese... 😞 ⚠ ⚠
    Klar, strlen o. ä. haben immer sowas stehen:

    while(*ptr)
    

    Nen' Null-Pointer zu dereferenzieren ist natürlich UB und führt zum crash.


Anmelden zum Antworten