[X] Sockets und das HTTP-Protokoll



  • Ich habe jetzt hinzugefügt, dass der Header ausgegeben wird, wenn ein Fehler auftrat. Außerdem habe ich jetzt eine Klasse erstellt, die von std::exception erbt (siehe Code).

    Bitte guckt euch das nochmal an, denn ich habe da ein Problem mit dem Destrutkur, denn wenn ich dessen Definition weglasse, klappt's nicht. Das find ich komisch, denn in Bespielen, die ich gelesen habe, wurde das nie so gemacht.

    Die Binär-Dateien habe ich noch nicht aktualisiert, hat sich ja auch nicht so viel geändert.

    mfg.



  • Joomoo, lade die Dateien doch bitte in das FTP-Verzeichnis des Magazins (in einen nach deinem Artikel benannten Ordner) hoch. Dann ist alles an einem Platz.

    Was das mit dem Konstruktor ist, weiß ich leider nicht.
    Falls du hier zu lange keine Antwort bekommst, frag doch mal im passenden Forum (C++?). 🙂



  • estartu schrieb:

    Joomoo, lade die Dateien doch bitte in das FTP-Verzeichnis des Magazins (in einen nach deinem Artikel benannten Ordner) hoch. Dann ist alles an einem Platz.

    Okay hab ich gemacht.

    Was das mit dem Konstruktor ist, weiß ich leider nicht.
    Falls du hier zu lange keine Antwort bekommst, frag doch mal im passenden Forum (C++?). 🙂

    Jo, könnt ich machen, aber ich glaube so ist's jetzt erstmal in Ordnung mit dem Code und ich arbeite weiter an dem Artikel.

    mfg.



  • Schau dir das mal an:
    Ich hab jetzt erstmal ein Programm geschrieben welches einfach Dateien vom Server runterläd. Hier ist die binäre Windows-Datei und hier die für Linux.

    Oder so ähnlich.
    Das sieht doch viel schöner aus als mit den Monsterlinks. 🙂

    Einfach: [url=http://www.blabla....]Text den man sehen soll[/url]



  • estartu schrieb:

    Schau dir das mal an:
    Ich hab jetzt erstmal ein Programm geschrieben welches einfach Dateien vom Server runterläd. Hier ist die binäre Windows-Datei und hier die für Linux.

    Oder so ähnlich.
    Das sieht doch viel schöner aus als mit den Monsterlinks. 🙂

    Einfach: [url=http://www.blabla....]Text den man sehen soll[/url]

    Danke, hab ich geändert.

    mfg.



  • joomoo schrieb:

    ~socketError() throw() {} // <- Ohne diese Zeile krieg ich:
    // overriding `virtual std::exception::~exception() throw ()'
    // Warum?

    Wenn Du von einer Klasse ableitest muss der Destruktor immer virtuell sein, da sonst das Verhalten deines Programmes beim Zerstören des Exception-Objektes undefiniert ist. Die throw-Spezifikation musst Du angeben, weil die Basis-Klasse den Destruktor mit der throw-Spezifaktion vorgibt. Du garantierst damit übrigens, dass der Destruktor niemals eine Exception wirft (Exception-Garantie).

    Der Typ einer Funktion

    void f(void)

    unterscheidet sich von

    void f(void) throw()

    Du kannst das überprüfen indem Du eine Funktions-Pointer-Variable auf die Funktionen zeigen lässt oder den typeid-Operator auf die Funktionen anwendest.

    Der Konstruktor

    socketError(int errorN, std::string errorS) : errorNumber_(errorN), errorString_(errorS) {}

    sollte besser errorS als const reference auf einen string übergeben bekommen.

    socketError(int errorN, const std::string & errorS) : errorNumber_(errorN), errorString_(errorS) {}
    

    und alternativ (vielleich auch zusätzlich) als char pointer initialisiert werden können

    socketError(int errorN, const char * errorS) : errorNumber_(errorN), errorString_(errorS) {}
    

    da sonst unnötige temporäre Kopien angelegt werden müssen.
    Objekte (auch string-Objekte) sollte man wann immer es möglich ist, als Referenz übergeben oder zurückgeben.



  • rik schrieb:

    joomoo schrieb:

    ~socketError() throw() {} // <- Ohne diese Zeile krieg ich:
    // overriding `virtual std::exception::~exception() throw ()'
    // Warum?

    Wenn Du von einer Klasse ableitest muss der Destruktor immer virtuell sein, da sonst das Verhalten deines Programmes beim Zerstören des Exception-Objektes undefiniert ist. Die throw-Spezifikation musst Du angeben, weil die Basis-Klasse den Destruktor mit der throw-Spezifaktion vorgibt. Du garantierst damit übrigens, dass der Destruktor niemals eine Exception wirft (Exception-Garantie).

    Der Typ einer Funktion

    void f(void)

    unterscheidet sich von

    void f(void) throw()

    Du kannst das überprüfen indem Du eine Funktions-Pointer-Variable auf die Funktionen zeigen lässt oder den typeid-Operator auf die Funktionen anwendest.

    danke für die Erklärung!
    Hat mich nur etwas gewundert da ich in Literatur noch nicht gesehen habe, dass jemand das macht wenn er von std::exception ableitet. Könnte es sein das best. Compiler das übersehen?

    Der Konstruktor

    socketError(int errorN, std::string errorS) : errorNumber_(errorN), errorString_(errorS) {}

    sollte besser errorS als const reference auf einen string übergeben bekommen.

    socketError(int errorN, const std::string & errorS) : errorNumber_(errorN), errorString_(errorS) {}
    

    und alternativ (vielleich auch zusätzlich) als char pointer initialisiert werden können

    socketError(int errorN, const char * errorS) : errorNumber_(errorN), errorString_(errorS) {}
    

    da sonst unnötige temporäre Kopien angelegt werden müssen.
    Objekte (auch string-Objekte) sollte man wann immer es möglich ist, als Referenz übergeben oder zurückgeben.

    danke! hab den tipp sogar noch gelesen bei effektiv C++ programmieren aber irgendwie nicht dran gedacht.

    mfg.



  • Bitte keine Binäries! Wir sind hier je eh ein einem Programmierer-Forum, da sollte man in der Lage sein, selbst zu kompilieren.



  • rüdiger schrieb:

    Bitte keine Binäries! Wir sind hier je eh ein einem Programmierer-Forum, da sollte man in der Lage sein, selbst zu kompilieren.

    Ok das am Anfang hab ich rausgenommen, aber im Artikel kann es doch drinn bleiben, oder?

    mfg.



  • @joomoo
    Schaffst du es, dass dein Artikel zur nächsten Runde fertig wird? Wird bräuchten nämlich noch einen, damit wir auf 2 Stück kommen.



  • GPC schrieb:

    @joomoo
    Schaffst du es, dass dein Artikel zur nächsten Runde fertig wird? Wird bräuchten nämlich noch einen, damit wir auf 2 Stück kommen.

    Momentan hatte ich gerade vor ein paar Wochen mein Praktikum und hab deswegen nicht so viel Zeit, aber ich denke ab Dienstag kann ich wieder weiter arbeiten. Mein Artikel wird dann wahrscheinlich Mitte Dezember fertig werden, dann setze ich ihn auf [T].
    Ihr könnt aber trotzdem jetzt schonmal rübergucken, ich uploade ihn in regelmäßigen Abständen.

    mfg.



  • So, hab den Artikel auf [T] gesetzt, da er bis auf das letzte Kapitel (welches nur noch ein paar Nebensächliche Sachen behandelt die nichts mit dem Thema zu tun haben) und die Linkliste fertig ist.

    An einigen stellen sicher noch einige Grammatikfehler da ich von Du auf Sie/Wir und jetzt auf Ihr/Wir umgeschaltet habe.

    mfg.



  • Mach doch aus

    #ifndef linux 
    // Startet WinSock 2 
    void StartWinsock() 
    { 
        WSADATA w; 
        if(WSAStartup(MAKEWORD(2,2), &w) != 0) 
        { 
            std::cout << "Winsock 2 konnte nicht gestartet werden! Error #" << WSAGetLastError() << std::endl; 
            exit(1); 
        } 
    }
    #endif
    

    ein

    void StartWinsock() 
    { 
    #ifndef linux 
      // Startet WinSock 2 
        WSADATA w; 
        if(WSAStartup(MAKEWORD(2,2), &w) != 0) 
        { 
            std::cout << "Winsock 2 konnte nicht gestartet werden! Error #" << WSAGetLastError() << std::endl; 
            exit(1); 
        } 
    #endif 
    }
    

    Dann kannst Du Dir ein späteres "#ifndef linux" hier sparen:

    int main() { 
        using namespace std; 
    
        StartWinsock();
    

    Auch würde sich dann Dein ersten Beispiel unter Linux übersetzen lassen 😉



  • Vielen Dank! Ich hab das ganze jetzt direkt in die main() Funktion geschrieben.

    mfg.


Anmelden zum Antworten