String umdrehen



  • Wir sollen eine Funktion schreiben, die einen String umdreht.
    Z.B. test123 soll zu 321tset werden.
    Das ist mein Programm, aber es funktioniert nicht richtig und crasht immer.
    Warum?

    std::string dreh(std::string input)
    {
    		std::string output;
    		for(size_t i = input.length()-1; i>=0; i-- )
    		{
    			output += input[i];
    		}
    		return output;
    }
    
    int main()
    {
    	std::string input = "test123";
    	std::cout << dreh(input);
    }
    


  • size_t ist vorteichenlos. i>=0 ist daher immer wahr. Damit ist das eine Endlosschleife. Weiterhin möchtest du den String input als Referenz und nicht als Kopie übergeben, sonst hat dreh keine Wirkung.



  • Ich bin ziemlich sicher, dein Compiler hätte dich warnen müssen.

    Es ist sehr löblich, dass du size_t verwendest, aber leider ist size_t unsigned, d.h. es kann keine negative Zahlen annehmen und ist damit immer >= 0.

    Ein Trick wäre

    size_t i = input.length(); i-->0;)
    


  • nwp3 schrieb:

    Weiterhin möchtest du den String input als Referenz und nicht als Kopie übergeben, sonst hat dreh keine Wirkung.

    Das macht er schon richtig.



  • std::string umdrehen(const std::string& input)
    {
        return std::string(input.rbegin(), input.rend());
    }
    

    Man kann einen String mit zwei iteratoren erzeugen, dass bedeutet einen Iterator auf den Anfang und einen auf das Ende des Strings. rbegin und rend erzeugen Iteratoren, die in die andere Richtung laufen.

    Das lohnt sich dann, wenn man einen neuen String erzeugen will. Arbeitet man hingegen auf dem gleichen, also so:

    foo = umdrehen(foo);
    

    dann sollte man

    std::reverse(std::begin(foo), std::end(foo));
    

    anwenden, denn man kann weiterhin im alten Speicher arbeiten und braucht keinen neuen.



  • underflow schrieb:

    nwp3 schrieb:

    Weiterhin möchtest du den String input als Referenz und nicht als Kopie übergeben, sonst hat dreh keine Wirkung.

    Das macht er schon richtig.

    Ups. WTB Löschfunktion.



  • Also so geht es jetzt.

    std::string dreh(const std::string& input)
    {
    		std::string output;
    		for(size_t i = input.length()-1; i-- >0; )
    		{
    			output += input[i];
    		}
    		return output;
    }
    
    int main()
    {
    	std::string input = "test123";
    	std::cout << dreh(input);
    }
    

    Marthog schrieb:

    std::string umdrehen(const std::string& input)
    {
        return std::string(input.rbegin(), input.rend());
    }
    

    Ist das besser als meines oder gibt es noch was anderes zum verbessern?



  • Es ist kürzer, übersichtlicher, es gibt keine Out-of-bound-errors und es macht keinen relevanten Geschwindigkeitsunterschied. Also: besser



  • MichaelBr schrieb:

    Marthog schrieb:

    std::string umdrehen(const std::string& input)
    {
        return std::string(input.rbegin(), input.rend());
    }
    

    Ist das besser als meines oder gibt es noch was anderes zum verbessern?

    std::string str = "test123";
    std::reverse(str.begin(), str.end());
    


  • Zumindest ist es kürzer und übersichtlicher 😉

    Edit: Darn, einfach zu langsam.



  • phanzy schrieb:

    Zumindest ist es kürzer und übersichtlicher 😉

    Edit: Darn, einfach zu langsam.

    😃 4 Sekunden.



  • vonwegen std::string und UTF-8 http://www.c-plusplus.net/forum/p2346091#2346091





  • Ethon, danke, danke, danke!
    Der Link hat mir die Ferien gerettet!
    Danke!
    👍



  • Das ganze Vorhaben ist unsinnig. Als Übungsaufgabe in Ordnung ("Wir sollen eine Funktion schreiben, die einen String umdreht."), aber aus Unicode-Sicht unmöglich.

    Wie willst du "œ" umdrehen? Wie "¨o" (Ein Graphem)? Als Beispiel wird "aü" codepointweise umgedreht zu "uä" (wenn als "a¨u" abgespeichert).

    Ja, std::string ist Unicode-aware, aber er schützt nicht vor falscher Benutzung. Wie der Java-String übrigens.

    (utf8-cpp hilft da überhaupt nicht, weil auf Codepoints zu operieren nichts bringt)



  • Natürlich klappt das mit utfcpp? Einfach rückwärts die Codepoints iterieren und den String zusammenbauen.



  • Ethon schrieb:

    Natürlich klappt das mit utfcpp? Einfach rückwärts die Codepoints iterieren und den String zusammenbauen.

    Codepoint != Zeichen, siehe mein Beispiel.


Anmelden zum Antworten