Stream Problem



  • Hallo erstmal und entschuldigt das neue Thema
    ich habe folgendes Problem in meinem Programm wenn ich die md's filescreated und hours_worked in der Console ausgebe zeigt er mir die richtigen Daten lasse ich sie aber in ein neues Textdokument speicher hab ich nur ein Teil meiner Daten.
    Wieso ?

    #include <iostream>
    #include <istream> 
    #include <fstream> 
    #include <limits>  
    #include <string>
    
    struct MD  // string für datum und doubles für  die werte in zahlen
    { 
        std::string datum; 
        double hours_worked; 
        double filescreated; 
    };
    
    namespace 
    { 
        const std::streamsize ALL = std::numeric_limits< std::streamsize >::max(); 
    }; 
    // filter :P
    std::istream& operator>>( std::istream& in, MD& md ) 
    { 
        in.ignore( ALL, '[' ) >> md.datum; 
        std::string token; 
        if( getline( in.ignore( ALL, '|' ), token, '=' ) ) 
        { 
            md.hours_worked = 0.;  
            md.filescreated = 0.; 
            if( token == "hours_worked" ) 
                in >> md.hours_worked; 
            else if( token == "filescreated" ) 
                in >> md.filescreated; 
            else 
                in.setstate( std::ios_base::failbit ); 
        } 
        return in; 
    }
    struct Komma : public std::numpunct< char > 
    { 
    protected: 
        virtual char_type do_decimal_point() const 
        { 
            return ','; 
        } 
    };
    
    int main() 
    { 
        using namespace std; 
        ifstream fin("C:/Ruby193/1.txt"); 
       fin.imbue( locale( fin.getloc(), new Komma ) );
        if( !fin.is_open() ) 
        { 
            cerr << "Fehler beim Oeffnen der Datei" << endl; 
    
            return -2; 
        } 
    
        for( MD md; fin >> md; ) 
        {  
               // md's   auswerten
              cout << md.datum << endl ;    
              cout <<  md.hours_worked << endl ;
              cout << md.filescreated << endl ;
    
              ofstream myFile;  
           myFile.open ("C:/Ruby193/fast.csv");
    
           if (myFile)
       {
          // in datei schreiben 
           myFile << md.datum << endl ;
           myFile << md.hours_worked << endl ;
           myFile << md.filescreated << endl ;
           myFile.close();
    
           }
    
             //   md's   summieren 
        } 
        if( fin.eof() ) 
        { 
    
        } 
        getchar () ;
        return 0; 
    }
    


  • Cevin19994 schrieb:

    Hallo erstmal und entschuldigt das neue Thema
    ich habe folgendes Problem in meinem Programm wenn ich die md's filescreated und hours_worked in der Console ausgebe zeigt er mir die richtigen Daten lasse ich sie aber in ein neues Textdokument speicher hab ich nur ein Teil meiner Daten.
    Wieso ?

    Vorschlag: verallgemeinere deine Serialisierung, in dem du den operator<< überlädst/eine Funktion schreibst, die in einen übergebenen Stream schreibt.

    Dein Problem ist übrigens, dass std::ofstream den Datei-Inhalt in der Schleife immer wieder überschreibt, weil der Dateizeiger beim Öffnen standardmäßig am Anfang platziert wird. Definiere den Stream also außerhalb der Schleife, und öffne auch die Datei außerhalb der Schleife, dann dürfte das laufen.

    (Eine andere Möglichkeit wäre, das Flag ios_base::ate anzugeben, aber trotzdem ist das vielfache Öffnen und Schließen unperformant).



  • Okay danke erstmal 🙂 ich habe es aus der schleife schon versucht aber dann kommt immer eine Fehlermeldung 😕



  • Cevin19994 schrieb:

    Okay danke erstmal 🙂 ich habe es aus der schleife schon versucht aber dann kommt immer eine Fehlermeldung 😕

    Wäre schön, wenn du die zitierst.
    Dann kann man dir helfen, weißt du.



  • 80 C:\Dev-Cpp\valueextractor.cpp name lookup of `md' changed for new ISO `for' scoping

    Das spuckt er mir aus wenn ich es außerhalb der Schleife mache

    jetzt nicht in zeile 80 sonder ich glaube in zeile 71 ... weil ich den code ja geändert hatte



  • Ach ich sehe gerade

    C:\Dev-Cpp\valueextractor.cpp cannot use obsolete binding at `md' because it has a destructor

    der fheler kommt aich in zeile 58



  • Cevin19994 schrieb:

    jetzt nicht in zeile 80 sonder ich glaube in zeile 71 ... weil ich den code ja geändert hatte

    Dann schick uns doch den geänderten Code 🙂

    gruß
    syntax



  • Hier der Code des ausführbaren Programms (wo text in consolen ausgabe stimmt aber nicht beim abspeichern in eine datei)

    #include <iostream>
    #include <istream> 
    #include <fstream> 
    #include <limits>  
    #include <string>
    
    struct MD  // string für datum und doubles für  die werte in zahlen
    { 
        std::string datum; 
        double hours_worked; 
        double filescreated; 
    };
    
    namespace 
    { 
        const std::streamsize ALL = std::numeric_limits< std::streamsize >::max(); 
    }; 
    // filter :P
    std::istream& operator>>( std::istream& in, MD& md ) 
    { 
        in.ignore( ALL, '[' ) >> md.datum; 
        std::string token; 
        if( getline( in.ignore( ALL, '|' ), token, '=' ) ) 
        { 
            md.hours_worked = 0.;  
            md.filescreated = 0.; 
            if( token == "hours_worked" ) 
                in >> md.hours_worked; 
            else if( token == "filescreated" ) 
                in >> md.filescreated; 
            else 
                in.setstate( std::ios_base::failbit ); 
        } 
        return in; 
    }
    struct Komma : public std::numpunct< char > 
    { 
    protected: 
        virtual char_type do_decimal_point() const 
        { 
            return ','; 
        } 
    };
    
    int main() 
    { 
        using namespace std; 
        ifstream fin("C:/Ruby193/1.txt"); 
       fin.imbue( locale( fin.getloc(), new Komma ) );
        if( !fin.is_open() ) 
        { 
            cerr << "Fehler beim Oeffnen der Datei" << endl; 
    
            return -2; 
        } 
    
        for( MD md; fin >> md;  ) 
        {  
               // md's   auswerten
               cout << "Datum      |   Stunden gearbeitet | Dateien erstellt " << endl ;
              cout << md.datum << "|          " << md.hours_worked << "          |          " << md.filescreated << endl ;    
    
              ofstream myFile;  
           myFile.open ("C:/Ruby193/fast.txt");
    
           if (myFile)
       {
          // in datei schreiben 
              myFile << "Datum      |   Stunden gearbeitet | Dateien erstellt " << endl ;
              myFile << md.datum << "|          " << md.hours_worked << "          |          " << md.filescreated << endl ; 
           myFile.close();
    
           }
    
             //   md's   summieren 
        } 
        if( fin.eof() ) 
        { 
    
        } 
        getchar () ;
        return 0; 
    }
    

    Hier der Code wo ofstream aus der schleife ist

    #include <iostream>
    #include <istream> 
    #include <fstream> 
    #include <limits>  
    #include <string>
    
    struct MD  // string für datum und doubles für  die werte in zahlen
    { 
        std::string datum; 
        double hours_worked; 
        double filescreated; 
    };
    
    namespace 
    { 
        const std::streamsize ALL = std::numeric_limits< std::streamsize >::max(); 
    }; 
    // filter :P
    std::istream& operator>>( std::istream& in, MD& md ) 
    { 
        in.ignore( ALL, '[' ) >> md.datum; 
        std::string token; 
        if( getline( in.ignore( ALL, '|' ), token, '=' ) ) 
        { 
            md.hours_worked = 0.;  
            md.filescreated = 0.; 
            if( token == "hours_worked" ) 
                in >> md.hours_worked; 
            else if( token == "filescreated" ) 
                in >> md.filescreated; 
            else 
                in.setstate( std::ios_base::failbit ); 
        } 
        return in; 
    }
    struct Komma : public std::numpunct< char > 
    { 
    protected: 
        virtual char_type do_decimal_point() const 
        { 
            return ','; 
        } 
    };
    
    int main() 
    { 
        using namespace std; 
        ifstream fin("C:/Ruby193/1.txt"); 
       fin.imbue( locale( fin.getloc(), new Komma ) );
        if( !fin.is_open() ) 
        { 
            cerr << "Fehler beim Oeffnen der Datei" << endl; 
    
            return -2; 
        } 
    
        for( MD md; fin >> md;  ) 
        {  
               // md's   auswerten
               cout << "Datum      |   Stunden gearbeitet | Dateien erstellt " << endl ;
              cout << md.datum << "|          " << md.hours_worked << "          |          " << md.filescreated << endl ;    
    
             //   md's   summieren 
        } 
        if( fin.eof() ) 
        { 
    
        } 
    
              ofstream myFile;  
           myFile.open ("C:/Ruby193/fast.txt");
    
           if (myFile)
       {
          // in datei schreiben 
              myFile << "Datum      |   Stunden gearbeitet | Dateien erstellt " << endl ;
              myFile << md.datum << "|          " << md.hours_worked << "          |          " << md.filescreated << endl ; 
           myFile.close();
    
           }
        getchar () ;
        return 0; 
    }
    

    Fehlermeldungen wen ofstream aus der schleife

    81 C:\Dev-Cpp\valueextractor.cpp name lookup of `md' changed for new ISO `for' scoping
    
    58 C:\Dev-Cpp\valueextractor.cpp cannot use obsolete binding at `md' because it has a destructor
    

  • Mod

    Das md in Zeile 58 hat nur innerhalb der Schleife Gültigkeit.



  • SeppJ schrieb:

    Das md in Zeile 58 hat nur innerhalb der Schleife Gültigkeit.

    das md in Zeile 8 gehört doch zur schleife ? also zur for-schleife
    🙂
    wie auch immer aber wenn ich den ofstream in der schleife lasse
    speichert er nicht alle zeilen von den md's
    und außerhalb der schleife gehts es ja nicht ! 😕
    wie löse ich dies am besten um alle md's komplett zum schreiben der neuen datei zu verwenden ?


  • Mod

    Cevin19994 schrieb:

    und außerhalb der schleife gehts es ja nicht ! 😕

    Das ist zwar nicht die Lösung, aber warum sollte das nicht gehen? Klar geht das!

    wie löse ich dies am besten um alle md's komplett zum schreiben der neuen datei zu verwenden ?

    Du musst dir erst einmal klar werden, was du überhaupt willst und welche Objekte wo beteiligt sind. Besonders den Punkt, was du überhaupt willst, scheinst du selber nicht zu wissen. Werner hat dir einen fast kompletten Code vorgesetzt, sogar mit Kommentaren, was wo zu machen wäre. Und du machst irgendwas komplett anderes, was irgendwie überhaupt nicht zu dem Vorhaben passt, was man dir in anderen Threads mit so viel Mühe aus der Nase gezogen hat. Wieso summierst du nicht einfach deine Werte?



  • Warum das nicht geht habe ich doch schon gepostet mit Fehlermeldungen !
    und ja Werner hat mir eine super Vorlage gegeben aber ich wollte auch was selber machen und bei dem was mir Werner vorgeschlagen hat kam ich nicht so klar da ich noch ein Anfänger bin ..
    wie man jetzt deutlich sehen kann 😛
    und warum ich dich werte nicht summiere ?
    erstens weiß ich noch nicht wie ich das mit den struckt objeckten machen soll 😕
    Wernders Vorschlag mit dem

    MD md;
    if (cin >> md){
    

    versteh ich nicht so ganz wegen der "cin" ?
    außerdem wenn ich noch nicht in der Lage bin den kompletten Inhalt der md's zu benutzen, was bringt mir das summieren ? wenn das Ergebnis auch nicht korrekt dargestellt wird ?
    Gruß Cevin 🙂



  • #include <iostream>
    #include <istream> 
    #include <fstream> 
    #include <limits>  
    #include <string>
    
     struct MD  // string für datum und doubles für  die werte in zahlen
    { 
       static std::string datum; 
        static double hours_worked; 
        static double filescreated; 
    };
    
    namespace 
    { 
        const std::streamsize ALL = std::numeric_limits< std::streamsize >::max(); 
    }; 
    // filter :P
    std::istream& operator>>( std::istream& in, MD& md ) 
    { 
        in.ignore( ALL, '[' ) >> md.datum; 
        std::string token; 
        if( getline( in.ignore( ALL, '|' ), token, '=' ) ) 
        { 
            md.hours_worked = 0.;  
            md.filescreated = 0.; 
            if( token == "hours_worked" ) 
                in >> md.hours_worked; 
            else if( token == "filescreated" ) 
                in >> md.filescreated; 
            else 
                in.setstate( std::ios_base::failbit ); 
        } 
        return in; 
    }
    struct Komma : public std::numpunct< char > 
    { 
    protected: 
        virtual char_type do_decimal_point() const 
        { 
            return ','; 
        } 
    };
    
    int main() 
    { 
        using namespace std; 
        ifstream fin ("C:/Ruby193/1.txt"); 
       fin.imbue( locale( fin.getloc(), new Komma ) );
        if( !fin.is_open() ) 
        { 
            cerr << "Fehler beim Oeffnen der Datei" << endl; 
    
            return -2; 
        } 
    
        for( MD md; fin >>  md ; ) 
        {  
               // md's   auswerten
               cout << "Datum        |Stunden gearbeitet | Dateien erstellt " << endl ;
              cout << md.datum << "|          " << md.hours_worked << "                |          " << md.filescreated << endl ;    
    
             // md's summierne
    
        } 
        if( fin.eof() ) 
        { 
    
           } 
    
              //md's schreiben 
              ofstream myFile;  
           myFile.open ("C:/Ruby193/md5.csv");
    
           if (myFile)
       {
    
              myFile << "Datum        |   Stunden gearbeitet | Dateien erstellt " << endl ;
              myFile << md.datum << "|          " << md.hours_worked << "                       |             " << md.filescreated << endl ; 
           myFile.close();
    
            }
    
        getchar () ;
        return 0; 
    }
    

    Hallo um nochmal auf SeppJ antwort zu kommen

    Das md in Zeile 58 hat nur innerhalb der Schleife Gültigkeit.

    Wie kann ich in diesem code den gültigkeitsbereich erweitern damit der so ausführbar ist ?


  • Mod

    Cevin19994 schrieb:

    Wie kann ich in diesem code den gültigkeitsbereich erweitern damit der so ausführbar ist ?

    SeppJ schrieb:

    Das ist zwar nicht die Lösung, aber warum sollte das nicht gehen? Klar geht das!

    Das ist genau das, was ich befürchtet habe. Du hast keinerlei Ahnung, was dieser Code zu bedeuten hat, wie er funktioniert oder was Werner sich dabei gedacht hat. Technisch korrekte Antwort (die beste Art von korrekt): Zieh das MD md; vor die for-Schleife.

    Hilfreiche Antwort ist die gleiche wie bisher: Lern endlich die Grundlagen von C++! Lern die Grundlagen der Programmierung allgemein! Lern an einfacheren Beispielen! So wird das nie etwas werden, außer irgendjemand erbarmt sich endlich mal zur Komplettlösung - die du dann auch nicht verstehen wirst. Wenn du nicht schon eine Woche an diesem Programm verschwendet hättest, wärst du in einem Grundlagenbuch längst bei Gültigkeitsbereichen und grundlegenden Programmstrukturen angelangt.



  • MD md ;
        for(  fin >>  md ; )
    

    So ?
    Das habe ich schon versucht ...


  • Mod

    Die Syntax einer for-Schleife sollte man vielleicht auch können, wenn man komplizierte Programme verändern möchte 🙄 . Das ist zweites oder drittes Kapitel im Grundlagenbuch. Stell dich nicht so lernfaul! Sonst hast du bald alle Helfer verschreckt. Ich glaube, ich bin sowieso der letzte mit Geduld für deine immer gleichen Fragen.



  • Ich habe 4 bücher von Dirk louis über c++ und das was übder die for schleife oder allgemein über schleifen steht ist nicht viel ..

    MD md ;
        for(  fin >>  md ; )
    

    das es so nicht geht weiß ich !

    aber als fehlermedlung bekomme ich nur das er noch ein ";" vor dem ")" will also

    MD md ;
        for(  fin >>  md ;; )
    

    dann ist das programm fehlerlos aber der linker macht probleme wegen den ganzen md's
    Aber wenn es besser so ist lese ich mir gerne noch das kapitel über die schleifen durch gruß cevin


  • Mod

    Cevin19994 schrieb:

    Ich habe 4 bücher von Dirk louis über c++ und das was übder die for schleife oder allgemein über schleifen steht ist nicht viel ..

    Wenn da nicht einmal Schleifen drin stehen, dann ist das wohl kein gutes Buch. Das ist wie eine Lesefibel ohne den Buchstaben 'A'. Guck mal den zweiten Link in meiner Signatur an.

    MD md ;
        for(  fin >>  md ;; )
    

    Das ist ja noch schlimmer. Das Forum ist kein Ersatz dafür, dass du nicht die Grundlagen lernen willst!



  • SeppJ ich weiß das es nicht gerade schön ist das ich mich so "dumm" anstelle
    aber wenn du mir nicht helfen willst versteh ich das ... wirklich ! aber dann mach mich nicht runter ... nur weil du viel über c++ zu wissen scheinst gibt es dir nicht das recht andere so zu behandeln .. ok ich habe bis jetzt versucht immer in meiner höfflichsten form mit jemanden zu schreiben ... egal was mich an der persohn stört !
    und ja ich weiß das es mit dem doppel ";;" auch nicht besser ist
    nur im synax der for schleife heißt es das bei den typischen fehlern es dau kommt das so welche ";" vergessen werden ... die initialisierung und die bedingung werden mit einem ";" abgeschlossen und die reinitialisierung ohne ";"
    Deshalb hab ichs halt mal ausprobiert !



  • Um den Thread mal zu beenden:

    MD md;
    for( ; fin >> md ; )
    {
      // ...
    }
    

    Oder besser gleich

    MD md;
    while (fin >> md)
    {
      // ...
    }
    

    Wenn in deinem C++ Buch wirklich nicht drin steht, wie man for in while Schleifen (und umgekehrt) überführen kann, dann würde es mich schon sehr wundern.


Log in to reply