Vector aus Strings durchsuchen



  • Ich versuche gerade ein File in einen Vector einzulesen und anschließend den Vector zu durchsuchen. Bisheriger Code:

    ConfigFile.open("Config.txt");
    	// If file exists
    	if (ConfigFile.is_open())
    	{
    		cout << "File found \n";
    
    		vector<string> FileContents;     
                    // Read file in vector
    		for (string RowFromFile; getline(ConfigFile, RowFromFile); )        
    			FileContents.push_back(RowFromFile);  
    
    		// Search for "Command:"
    		string SearchString ("Command:");
    		vector<string>::iterator Iterator;
    		Iterator = find(FileContents.begin(), FileContents.end(), SearchString.c_str());
    
    		if (Iterator == FileContents.end())
    			cout << "Not found.";
    		else
    			cout << *Iterator << " was found.";
    [...]
    

    Das funktioniert allerdings nur wenn in meinem File "Command:" allein als Zeile dasteht. Mein File sieht allerdings so aus:
    Command:INIT
    und ich möchte das entsprechend parsen. Ich habe leider nichts passendes gefunden und online finden sich fast nur Beispiele wie man in Strings sucht oder einzelne Zeichen oder Integer Werte aus einem Vektor rausholen kann.



  • Erstens: An dieser Stelle brauchst du den c_str() Aufruf nicht (der bremst dich nur aus).

    Zweitens: Dafür gibt es find_if:

    struct starts_with : public unary_function<string,bool>
    {
      starts_with(const string& value) : m_val(value);
      bool operator()(const string& data)
      { return data.find(m_val)==0; }
    private:
      const string& m_val;
    };
    
    ...
    Iterator = find_if(FileContents.begin(),FileContents.end(),starts_with(SearchString));
    ...
    


  • Super, danke hat funktioniert.


  • Mod

    CStoll schrieb:

    Erstens: An dieser Stelle brauchst du den c_str() Aufruf nicht (der bremst dich nur aus).

    Zweitens: Dafür gibt es find_if:

    struct starts_with : public unary_function<string,bool>
    {
      starts_with(const string& value) : m_val(value);
      bool operator()(const string& data)
      { return data.find(m_val)==0; }
    private:
      const string& m_val;
    };
    
    ...
    Iterator = find_if(FileContents.begin(),FileContents.end(),starts_with(SearchString));
    ...
    

    Ein paar mehr Gedanken sollte man sich schon noch machen:
    1. Zunächst einmal sind Referenzen ziemlich bösartige Klaasenmitglieder. Im Allgemeinen ist es keine gute Idee sie ohne besonderen Grund zu verwenden. Die Kopierbarkeit beeinträchtigt es nicht, aber es sind Algorithmen denkbar (wohl nicht die aus der Standardbibliothek), die diese auch einmal zuweisen wollen.
    2. Zudem hat das Funktionsobjekt keinen echten state, der member m_val ist ja eigentlich eher so etwas wie ein gebundener Parameter. Dann ist es logisch richtig, wenn unser Operator() konstant ist.
    3. Fliegt uns das Ganze um die Ohren, wenn jemand auf die Idee kommt, hier den Konstruktor mit einem Literal zu führen - das hat auch etwas mit Punkt 1 zu tun.
    Gedankenloses Ersetzen von Objekten durch Referenzen ist nicht ohne Tücken.

    also:

    struct starts_with : public unary_function<string,bool>
    {
      starts_with(const string& value) : m_val(value) {}
      bool operator()(const string& data) const
      { return data.find(m_val)==0; }
    private:
      string m_val;
    };
    

Anmelden zum Antworten