Konzeptfrage zu größerem Projekt



  • Hallo, ich lerne seit einiger Zeit C++. Nun wollte ich mich mit ein paar Freunden mal an ein größeres Projekt wagen.
    Da wir nicht viel Erfahrung im Erstellen von libraries haben, möchte ich mal eure Meinung zu zwei Themen wissen:
    1. Das Projekt soll eine Art mathematische Bibliothek werden. Im Rahmen dessen wollen wir teilweise auch auf Bitebene agieren. Dazu müssen wir die Endianess kennen, die der Compiler/das OS benutzt. Im Moment regeln wir das ganze so:

    #ifndef ENDIANESS
        #define ENDIANESS 1  // 1 = Little, 2 = Big
    #endif
    

    Also der benutzer muss ein Macro namens "ENDIANESS" definieren, mit dem entsprechenden Wert. Eine Andere Möglichkeit wäre, dies automatisch erkennen zu lassen:

    static const std::size_t n = 1;
    static const endianess = *(char*)&n & 1;
    
    template<std::size_t ENDIANESS = endianess> 
    class Whatever;
    
    template<>
    class Whatever<0>
    {
        //....
    };
    
    template<>
    class Whatever<1>
    {
        //....
    };
    

    Also die Endianess als default Template Parameter zu übergeben, was aber ggf. zu sehr viel Codedopplung führen könnte.
    Welchen Weg würdet ihr wählen? Vielleicht einen ganz anderen?

    2. Wie sollen wir regieren, wenn Fehler auftreten (zB. Division durch 0)?
    Im Moment haben wir folgenden Ansatz:

    #ifndef stream
       #define stream std::cerr
    #endif
    
    Whatever& operator/=(const Whatever& obj)
    {
        #ifdef IO_ERROR
        if(obj.is_null())
        {
            stream << "Division by Zero";
        }
        #endif
        #ifdef THROW_EXCEPTION
        if(obj.is_null())
        {
            throw meine_exception("Division by Zero");
        }
        #endif
    }
    

    Sodass sowohl Exception geworfen werden können als auch Fehler in einem stream geloggt werden können.
    Allerdings haben wir die Befürchtung, dass es ein wenig übertrieben ist, bei jedem kleinen Fehler eine Exception zu werfen.
    Außerdem haben wir uns dagegen entschieden, jeder Klasse einen Member zu geben, mit dem man den Status abfragen kann (ähnlich den Errorflags der std::streams).
    Wie würdet ihr auf solche Fehler reagieren?

    Schonmal Danke für alle Anregungen 😃



  • bool littleEndian()
    {
        short s = 1;
        return (((char*)&s)[0]) == 1;
    }
    

  • Mod

    Außerdem sollte man noch prüfen, ob überhaupt genau die Endianess und genau die Rechengenauigkeit der Datentypen vorliegt, von der ihr ausgeht. Es gibt nämlich sehr viel mehr als zwei Möglichkeiten bei der Endianess.

    Zur Fehlerbehandlung: Nichts ausgeben, dass irritiert nur. Exceptions sind ein Ansatz, der ok ist. Am besten auch wahlweise mit Exceptions oder ohne. Aber bei einer mathematischen Bibliothek bin ich sowieso verwundert, wo da Fehler auftreten sollen. Ich wäre entsetzt, wenn ein Programm einen Fehler erzeugt, wenn ich durch Null teile. Schonmal was von inf gehört? Oder nan? Damit sollte man eigentlich fast alle "Fehler" abdecken können.



  • #ifndef ENDIANESS
        #define ENDIANESS 1  // 1 = Little, 2 = Big
    #endif
    

    Ja, klar. Und einfach gegen Kóyaánasqatsis Funktion asserten.

    Whatever& operator/=(const Whatever& obj)
    {
        #ifdef IO_ERROR
        if(obj.is_null())
        {
            stream << "Division by Zero";
        }
        #endif
        #ifdef THROW_EXCEPTION
        if(obj.is_null())
        {
            throw meine_exception("Division by Zero");
        }
        #endif
        tuwas();
    }
    

    Das will keiner, fürchte ich.

    Whatever& operator/=(const Whatever& obj)
    {
        if(obj.is_null())
        {
            error("Division by Zero");
        }
        tuwas();
    }
    

    Ob error jetzt exit macht oder eine Exception wirft und mitloggt oder nicht, ist dann eine andere Geschichte. Ich würde es bei /= sogar bei assert belassen und assert wäre ein Makro, das mich falls vorhanden in den Debugger wirft, und dann eine Exception mit Dateiname und Zeilennummer wirft, die in der main() gefangen werden soll.


Log in to reply