Datei auslesen mit Inserter
-
Hallo,
ich habe eine Textdatei, in der beliebig viele durch Leerzeichen getrennte Ganzzahlen stehen. Diese sollen nun in einen vector<int> übertragen werden.Gibt es dafür eine schöne Möglichkeit mit back_inserter oder muss ich das mit einer temporären Variable und push_back lösen?
-
std::vector<int> v; std::ifstream is("foo.txt"); std::copy(std::istream_iterator<int>(is), std::istream_iterator<int>(), std::back_inserter(v));
-
Du brauchst back_inserter, copy und istream_iterator, dann kannst du damit einen Einzeiler schreiben. Die genaue Form lasse ich dir erst einmal zur Übung, die Beispiele zu den Links zeigen schon fast alles was du brauchst, du musst es nur noch richtig kombinieren.
edit: Zu spät. Siehe Pis Zeile 3.
-
es geht auch ohne back_inserter ..
std::ifstream is( "foo.txt" ); std::vector<int> v( (std::istream_iterator< int >( is )), std::istream_iterator< int >() );Bem.: die extra-Klammer um den ersten Parameter ist bei einigen Compilern notwendig.
Gruß
Werner
-
Werner Salomon schrieb:
Bem.: die extra-Klammer um den ersten Parameter ist bei einigen Compilern notwendig.
Schreib doch gleich MSVC hin. Ein weiterer Punkt für mich.
-
Danke für den Hinweis auf istream_iterator.
Mit int klappt es auch, aber bei z.B. pair<int, string> gibt es einen Compile-Fehler.
#include <stdafx.h> #include <string> #include <iostream> #include <fstream> #include <vector> #include <algorithm> #include <regex> #include <iterator> using namespace std; istream& operator>>(istream& is, pair<int, string>& obj) { string line; getline(is, line); cmatch matches; regex rex("(\\d+)\\|(\\w+)"); regex_search(line.c_str(), matches, rex); obj.first = strtol(matches[1].str().c_str(), 0, 0); obj.second = matches[2]; return is; } int main() { const char* filename = "test.txt"; ifstream file(filename); istream_iterator< pair<string, int> > str_iter(file); istream_iterator< pair<string, int> > end_iter; vector< pair<int, string> > vec(str_iter, end_iter); file.close(); for (vector< pair<int, string> >::iterator iter = vec.begin(); iter != vec.end(); ++iter) { cout << iter->first << ' ' << iter->second << '\n'; } return 0; }error C2678: Binärer Operator '>>': Es konnte kein Operator gefunden werden, der einen linksseitigen Operanden vom Typ 'std::basic_istream<_Elem,_Traits>' akzeptiert (oder keine geeignete Konvertierung möglich)
-
Das hängt mit dem Lookup zusammen. Der Compiler sucht nur im Namensraum
stdnach dem Operator, dort wird er ihn nicht finden.Zwei Möglichkeiten:
- Du fügst deinen Operator zu
stdhinzu (nicht schön!) - Du wrappst einfach dein
std::pair<int, string>in eine eigenestruct MyPair
Hier sollte dann ADL auch funktionieren.
BTW:
Wurstinator schrieb:
istream_iterator< pair<string, int> > str_iter(file); istream_iterator< pair<string, int> > end_iter; vector< pair<int, string> > vec(str_iter, end_iter);Typen vertauscht

- Du fügst deinen Operator zu
-
Den operator zu std hinzuzufügen klappt leider auch nicht:
#include <stdafx.h> #include <string> #include <iostream> #include <fstream> #include <vector> #include <algorithm> #include <regex> #include <iterator> using namespace std; namespace std { istream& operator>>(istream& is, pair<int, string>& obj) { string line; getline(is, line); cmatch matches; regex rex("(\\d+)\\|(\\w+)"); regex_search(line.c_str(), matches, rex); obj.first = strtol(matches[1].str().c_str(), 0, 0); obj.second = matches[2]; return is; } } int main() { const char* filename = "test.txt"; ifstream file(filename); istream_iterator< pair<string, int> > str_iter(file); istream_iterator< pair<string, int> > end_iter(); vector< pair<string, int> > vec;//(str_iter, end_iter); file.close(); for (vector< pair<string, int> >::iterator iter = vec.begin(); iter != vec.end(); ++iter) { cout << iter->first << ' ' << iter->second << '\n'; } return 0; }Oder habe ich dich da falsch verstanden?
Typen vertauscht

Ups

-
Aquae schrieb:
Du fügst deinen Operator zu
stdhinzu (nicht schön!)nicht erlaubt!
-
@Wurstinator: Schau dir mal Signatur deines
operator>>an, insbesondere die Typen-Reihenfolge vonpair
-
Aquae schrieb:
@Wurstinator: Schau dir mal Signatur deines
operator>>an, insbesondere die Typen-Reihenfolge vonpair
Ich vermisse einen Head-Desk-Smiley

Danke. Bei der Fehlersuche habe ich die beiden Typen getauscht, aber wohl nicht überall daran gedacht.
-
Wurstinator schrieb:
Ich vermisse einen Head-Desk-Smiley

Danke. Bei der Fehlersuche habe ich die beiden Typen getauscht, aber wohl nicht überall daran gedacht.
Ich dachte, das hättest du mitWurstinator schrieb:
Typen vertauscht

Ups

schon gemeint. Sonst hatte ich dir das nämlich auch schon vor einer Stunde sagen können.
