Textfile nach String durchsuchen



  • Hallo,

    ich möchte ein Textfile einlesen und dieses durchsuchen. Das Einlesen und von Zeile zu Zeile springen geht schon. Leider schaffe ich es nicht mit dem find Befehl nach einem bestimmten Word zu suchen.🤔 Kann mir jemand einen Tipp geben was ich falsch mache 😬

    #include "stdafx.h"
    #include <stdio.h>
    #include <tchar.h>
    
    #include <vector>
    #include <fstream>
    #include <iostream>
    #include <string>
    using namespace std;
    
    
    int main(int argc, char* argv[])
    {
    	ifstream InputFile;
    	char zeile[1024];
    	InputFile.open("D:\\Temp\\TestFile.a", ios::in);
    		if (InputFile.good())
    		{
    			// File could open
    			cout << "File opened." << endl;
    			// Start on file position 0
    			InputFile.seekg(0L, ios::beg);
    
    			while (!InputFile.eof())
    			{
    				// Find cow
    				InputFile.getline(zeile, 1024);
    				cout << zeile << endl;
    				vector <int>::iterator pos;
    				pos = find(zeile[0], zeile[1024], "Cow");
    				cout << pos << endl;
    
    			}
    		}
    		else
    		{
    			// File is not readable
    			cout << "File not found." << endl;
    		}
    
    	InputFile.close();  // Close file
    
    	system("PAUSE");  // Break, to read the console
        return 0;
    }
    

    Das Textfile sieht wie folgt aus.

    Hier steht text.
    Schlange Affe
    Pflaume Baum
    Mouse Cow
    Haase Igel
    
    


  • @ollom sagte in Textfile nach String durchsuchen:

    Leider schaffe ich es nicht

    Und das bedeutet?



  • Verwende für Strings in C++ std::string, nicht char-Arrays.

    Was soll das

    vector <int>::iterator pos;
    pos = find(zeile[0], zeile[1024], "Cow");
    

    machen?



  • Oh sorry, das habe ich beim Vereinfachen für das Beispiel übersehen.
    Das sollte eigentlich folgender Maßen aussehen.

    int pos;
    pos = find(zeile[0], zeile[1024], "Cow");
    

    Dies sollte mir die Position in der Zeile zurück geben an der das Wort Cow steht.

    Ich bekomme aber immer einen Fehler in der xutility den ich nicht verstehe.

    Fehler C2794:"iterator_category": Kein Element einer direkten oder indirekten Basisklasse von "std::iterator_traits<_InIt>";	
    Fehler C2938:"_Iter_cat_t<char>": Spezialisierung der Aliasvorlage fehlgeschlagen;	
    Fehler C2062:"unknown-type"-Typ unerwartet	
    


  • Am besten du öffnest die Datei und schreibst den gesamten Inhalt in einen std::string. Dieser bietet dir dann die Methoden std::string::find() zum finden eines einzelnen Zeichens oder einer Zeichenkette.

    Andererseits läufst du in die Gefahr, dass der gesuchte Term zufälligerweise nur halb extrahiert wird und du den Term niemals finden wirst. Natürlich kannst du das auch so machen - wäre sogar speicherfreundlicher - aber dann solltest du mit seekg() jedes Mal ein Stück zurückgehen.



  • Leider ist mir nicht ganz klar was du meinst. Ersetze ich das ifstream InputFile; durch std::string InputFile fallen doch die ganzen Funktionen wie open, getline und good weg. Oder meintest du das nur für die Zeile?

    Mir ist auch nicht klar warum ich jedes mal ein Stück zurück gehen soll mittel seekg(). Die getline Funktion geht doch Zeile für Zeile durch und das find soll die Zeile von 0 bis 1024 angucken.



  • @ollom sagte in Textfile nach String durchsuchen:

    int pos;
    pos = find(zeile[0], zeile[1024], "Cow");
    

    Dies sollte mir die Position in der Zeile zurück geben an der das Wort Cow steht.

    Ich bekomme aber immer einen Fehler in der xutility den ich nicht verstehe.

    Fehler C2794:"iterator_category": Kein Element einer direkten oder indirekten Basisklasse von "std::iterator_traits<_InIt>";	
    Fehler C2938:"_Iter_cat_t<char>": Spezialisierung der Aliasvorlage fehlgeschlagen;	
    Fehler C2062:"unknown-type"-Typ unerwartet	
    

    Ist zeile[0]ein Iterator des Arrays?
    ist int pos ein Iterator des Arrays?
    Ist "Cow" mit einem char vergleichbar?

    Benutze std::string Zeile;. std::string hat eine eigene find Funktion.



  • @Ollom, nein du sollst ifstream nicht mit string ersetzen, sondern mittels ifstream sofort den ganzen Dateiinhalt in den String schreiben.

    Da gibt es einige Möglichkeiten.

    int main(){
        std::ifstream stream{"file.txt"};
    
        if(!stream.is_open())
            throw;
    
        // entweder so
        {
            std::stringstream ss;
            ss << stream.rdbuf();
            std::string content = ss.str();
        }
    
        // oder so
        {
            stream.seekg(0, std::ios::end);
            auto size = stream.tellg();
            stream.seekg(0, std::ios::beg);
            std::string content(size, '\0');
            stream.read(&content[0], size);
        }
    }
    

    @ollom sagte in Textfile nach String durchsuchen:

    Mir ist auch nicht klar warum ich jedes mal ein Stück zurück gehen soll mittel seekg(). Die getline Funktion geht doch Zeile für Zeile durch und das find soll die Zeile von 0 bis 1024 angucken.

    Das kommt halt darauf an. Wenn du dir sicher bist, dass dein Suchterm immer voll und ganz in einer Zeile steht, dann brauchst du das auch nicht, ja.

    Und wenn dem so sein soll, kein Problem, aber dann würde ich die freie Funktion std::getline(stream, line) verwenden, das Teil ist nicht nur auf 1024 Bytes beschränkt.



  • @spiri sagte in Textfile nach String durchsuchen:

    Am besten du öffnest die Datei und schreibst den gesamten Inhalt in einen std::string

    Das mag für ein kleines Beispiel funktionieren, aber spätestens bei Gigabyte großen Dateien ist das dann nicht besonders schlau.



  • Hallo,

    ich habe mal eure Hinweise umgesetzt und auch Kommentare dran geschrieben was ich erwarte.
    Im Moment habe ich aber das Problem, dass ich gar nicht mehr in die While Schleife rein komme. Kann es sein das die Funktion .eof nicht mehr funktioniert?

    #include "stdafx.h"
    #include <stdio.h>
    #include <tchar.h>
    
    #include <vector>
    #include <fstream>
    #include <iostream>
    #include <string>
    using namespace std;
    
    
    int main(int argc, char* argv[])
    {
    	std::ifstream InputFile;
    	InputFile = {"D:\\Temp\\TestFile.a"};
    	
    		// Look for Cow
    		if (InputFile.is_open())
    		{
    			// File could open
    			cout << "File opened." << endl;
    			
    			// Start on file position 0
    			InputFile.seekg(0, std::ios::end);	// Kursor auf Endposition
    			auto size = InputFile.tellg();		// Checke größe
    			InputFile.seekg(0, std::ios::beg);	// Kursor an den Anfang
    			std::string content(size, '\0');	// String mit entsprechender Größe und Abschluss
    			InputFile.read(&content[0], size);	// Daten werden in das InputFile geschrieben
    			
    
    			while (!InputFile.eof())
    			{
    				cout << "1" << endl; // Nur zum Schauen ob ich in die Schleife komme
    				// Find cow
    				std::string line;
    				std::getline(InputFile, line);
    				cout << line << endl;
    				std::string::size_type pos;
    				pos = line.find("Cow");
    				cout << pos << endl;
    
    			}
    		}
    		else
    		{
    			// File is not readable
    			cout << "File not found." << endl;
    		}
    		
    	InputFile.close();  // Close file
    
    	system("PAUSE");  // Break, to read the console
        return 0;
    }
    

    @spiri sagte in Textfile nach String durchsuchen:

    Das kommt halt darauf an. Wenn du dir sicher bist, dass dein Suchterm immer voll und ganz in einer Zeile steht, dann brauchst du das auch nicht, ja.
    Und wenn dem so sein soll, kein Problem, aber dann würde ich die freie Funktion std::getline(stream, line) verwenden, das Teil ist nicht nur auf 1024 Bytes beschränkt.

    Bedeutet "voll und ganz " das dass gesamte Wort irgendwo in der Zeile steht oder darf nur das gesuchte Wort in der Zeile stehen?



  • Dude, du hast doch den ganzen Dateiinhalt in die string-Variable content geschrieben.

    Jetzt machst du nur noch ein auto pos = content.find("Cow"); und gut is.



  • @spiri sagte in Textfile nach String durchsuchen:

    Dude, du hast doch den ganzen Dateiinhalt in die string-Variable content geschrieben.
    Jetzt machst du nur noch ein auto pos = content.find("Cow"); und gut is.

    😳
    Besten Dank für eure Hilfe. So habe ich es mir vorgestellt.🙏🏻



  • Ich muss das Thema doch noch mal aufgreifen. Wie kann ich denn die Suche umbauen, sodass ich die Zeile als Ausgabe bekomme?



  • @ollom sagte in Textfile nach String durchsuchen:

    Ich muss das Thema doch noch mal aufgreifen. Wie kann ich denn die Suche umbauen, sodass ich die Zeile als Ausgabe bekomme?

    Zeilen statt Dateien einlesen?



  • @ollom sagte in Textfile nach String durchsuchen:

    Ich muss das Thema doch noch mal aufgreifen. Wie kann ich denn die Suche umbauen, sodass ich die Zeile als Ausgabe bekomme?

    Somit:

    while(std::getline(stream, line))
      std::cout << line << '\n';
    

Anmelden zum Antworten