Hilfe: Caesar Verschlüssung in C++



  • nicht if ( geheim[i] > 'z' )
    sondern while (geheim[i] > 'z' )

    das würde schonmal besser funktionieren. Wie wurde früher die Caesar-Verschlüsselung realisiert? Richtig, mit so einer Art Drehscheibe. Die konnte man auch öfter als einmal verdrehen, das heißt eine Implementierung in c++ ohne so ein komisches "%" (Modulo!!) geht ein wenig an der ursprünglichen Idee vorbei



  • swapper schrieb:

    machs doch mit nem array arr = "abcdefghijklmnopqrstuvwxyz" aus dem input-zeichen c wird dann mit index = tolower (c)-'a' der index ermittlt und mit dem verschiebewert v dann zu c2 = arr[(index+v)%26], also dem verschlüsselten zeichen.

    Und das gleiche nochmal für Großbuchstaben?
    Dem Mann fehlt ganz offensichtlich alles an Grundlagen, dann konfrontiere ihn nicht mit dermaßen komplizierten Vorschlägen.

    Was soll denn dabei rauskommen wenn ich 'z' um 55 Positionen nach hinten verschiebe? Natürlich ein Sonderzeichen.

    Modulo ist auch keine Lösung. 😉



  • Meiner Meinung nach funktioniert sein erstes Programm!

    Er muss nur

    1. Diese komische "+2" durch "+ v" ersetzen

    2. Direkt nach dem einlesen von v
      v %= 26; ( Ohhhhh, ein Modulo, Caesar wird langsam aufhören, im Grabe zu rotieren und überlässt das lieber seiner Scheibe 😉 )
      einfügen, damit nur Buchstaben kommen.

    3. Sonderzeichen sollten vielleicht nicht mit verschlüsselt werden, ist aber Geschmackssache.

    und natürlich die falsche Schlussbedingung in der for-Schleife, aber das wurde ja schon genannt.

    Ich finde es schade, dass hier dermaßen auf dem TE herumgehackt wird. Er stellt eine einfache Frage, auf die es eine einfache Antwort gibt. Sein Programm hat eine ganz eigene "Eleganz", aber an sich ja funktional. Hier kommen dann eigene Lösungen, die mit vermutlich sehr viel Hintergrund-Wissen und jahrelanger Erfahrung erstellt wurden, und dann regt man sich auf, dass der TE damit überfordert ist...

    Deine erste Lösung war für einen Neuling sehr ordentlich, lass dir nichts anderes einreden!



  • gast12987897 schrieb:

    Ich finde es schade, dass hier dermaßen auf dem TE herumgehackt wird.

    Das habe ich nicht - im Gegenteil, ich habe ihm mehrere helfende Hände gereicht.



  • EOP schrieb:

    Und das gleiche nochmal für Großbuchstaben?

    nö, das programm macht einfach gnadenlos großbuchstaben zu kleinbuchstaben (oder umgekehrt). normalerweise ist groß oder klein dem caesar unbekannt. ziffern und satzzeichen etc. auch nicht. den ollen römern stellte sich das problem einfach nicht.



  • swapper schrieb:

    EOP schrieb:

    Und das gleiche nochmal für Großbuchstaben?

    nö, das programm macht einfach gnadenlos großbuchstaben zu kleinbuchstaben (oder umgekehrt). normalerweise ist groß oder klein dem caesar unbekannt. ziffern und satzzeichen etc. auch nicht. den ollen römern stellte sich das problem einfach nicht.

    PHP str_rot13 berücksichtigt auch GROß und klein.



  • Hallo,

    zuerst einmal danke an alle.

    Es funktioniert, bzw. geht in die richtige richtung.
    Eingabe: abc def xyz!ABC XYZ?
    Verschiebe um 3:

    Ausgabe: def ghi abc$DEF []B

    Sollte aber sein:

    def ghi abc!DEF ABC?

    ____
    2. Beispiel:
    Eingabe: Abc Zyx!
    Verschiebe um 55

    Ausgabe: Def ]ba$

    Sollte aber sein:

    Def Cba!

    Ich bin so nah am Ziel! Die Frage ist nur, wieso stehen dort sonderzeichen, obwohl ich die mit IF ausgeschlossen habe? Normalerweise sollten es buchstaben ergeben, wieso ergeben es Sonderzeichen?

    #include <iostream>
    #include <string>
    
    using namespace std;
    int main() {
    
    	string text;
    	int v;
    	string geheim;
    	cout << "Bitte geben Sie den zu verschluesselnden Text ein: ";
    	getline(cin, text);
    
    	cout << "Bitte geben Sie die Anzahl Verschiebepositionen ein (als positive ganze Zahl): ";
    	cin >> v;
    	v %= 26;
    	for (int i = 0; i < text.length(); i++) {
    
    		if(text[i] >= 65 && text[i] <= 122) {
    
    			geheim += static_cast<unsigned>(text[i]) + v;
    
    			if (static_cast<unsigned>(geheim[i]) > 'z') {
    				geheim[i] = static_cast<unsigned>(geheim[i]) - (v / 26 + 1) * 26;
    			}
    
    		}
    		else {
    			geheim += text[i];
    		}
    
    	}
    
    	cout << geheim << endl;
    	system("pause");
    
    }
    


  • EOP schrieb:

    swapper schrieb:

    EOP schrieb:

    Und das gleiche nochmal für Großbuchstaben?

    nö, das programm macht einfach gnadenlos großbuchstaben zu kleinbuchstaben (oder umgekehrt). normalerweise ist groß oder klein dem caesar unbekannt. ziffern und satzzeichen etc. auch nicht. den ollen römern stellte sich das problem einfach nicht.

    PHP str_rot13 berücksichtigt auch GROß und klein.

    um das zu erreichen, kann sich der code ja merken, ob das zeichen vorher groß war und es dann wieder groß machen. dafür ist bei rot13 der verschiebefaktor festgenagelt.

    beispiel:

    /**
     * rotate one char like cesar did. (but case preserving) ;)
     * @param c input char
     * @param v steps to rotate
     * @return rotated char (if it is a letter)
     */
    char rot (char c, int v)
    {
        static char* arr = "abcdefghijklmnopqrstuvwxyz";
        if (isalpha(c))
        {
            char low = tolower(c);
            char out = arr[(low-'a'+v)%26];
            return low == c ? out : toupper(out);
        }
        return c; // not a letter
    }
    


  • SvenJungwird schrieb:

    Es funktioniert, bzw. geht in die richtige richtung.
    Eingabe: abc def xyz!ABC XYZ?
    Verschiebe um 3:

    Ausgabe: def ghi abc$DEF []B

    Sollte aber sein:

    def ghi abc!DEF ABC?

    Gibt bei meiner Funktion dein erwartetes Ergebnis aus.
    Funktioniert mit -3 dann auch rückwärts.
    Alles kontrolliert.

    Über die Unsinnigkeit des Faktors 55 müssen wir uns nicht weiter unterhalten bevor du nicht den Aufbau der ASCII-Tabelle verinnerlicht hast.

    Die Caesar-Verschlüsseling ist nicht für Zahlen oder gar Sonderzeichen gedacht.



  • EOP schrieb:

    Über die Unsinnigkeit des Faktors 55 müssen wir uns nicht weiter unterhalten bevor du nicht den Aufbau der ASCII-Tabelle verinnerlicht hast.

    einspruch: ne caesar-chiffre sollte mit jedem beliebigen rotationsfaktor klar kommen und auch die ascii-table nicht unbedingt als in stein gemeißelt ansehen.



  • swapper schrieb:

    EOP schrieb:

    Über die Unsinnigkeit des Faktors 55 müssen wir uns nicht weiter unterhalten bevor du nicht den Aufbau der ASCII-Tabelle verinnerlicht hast.

    einspruch: ne caesar-chiffre sollte mit jedem beliebigen rotationsfaktor klar kommen und auch die ascii-table nicht unbedingt als in stein gemeißelt ansehen.

    Wohin schiebe ich dann denn z.B. eine '0' (ASCII #48)?



  • EOP schrieb:

    swapper schrieb:

    EOP schrieb:

    Über die Unsinnigkeit des Faktors 55 müssen wir uns nicht weiter unterhalten bevor du nicht den Aufbau der ASCII-Tabelle verinnerlicht hast.

    einspruch: ne caesar-chiffre sollte mit jedem beliebigen rotationsfaktor klar kommen und auch die ascii-table nicht unbedingt als in stein gemeißelt ansehen.

    Wohin schiebe ich dann denn z.B. eine '0' (ASCII #48)?

    die ist vom caesar nicht betroffen, da sie kein buchstabe ist.



  • Das ist doch auch einfacher möglich oder nicht ?



  • Gast267282 schrieb:

    Das ist doch auch einfacher möglich oder nicht ?

    Na dann hau raus.



  • Er muss nur
    C++:
    if (static_cast<unsigned>(geheim[i]) > 'Z') {
    geheim[i] = static_cast<unsigned>(geheim[i]) - (v / 26 + 1) * 26;
    }

    prüfen. Dann stimmt der vordere Teil aber nicht.



  • Hallo Gast, Hallo @all.

    Dieser Thread ist ja fast mit Antworten explodiert.

    Ich habe, dank euch einiges dazu gelernt, dafür vielen Dank.

    Die Lösung ist:

    #include <iostream>
    #include <string>
    
    using namespace std;
    int main() {
    
    	string text;
    	int v;
    	string geheim;
    	cout << "Bitte geben Sie den zu verschluesselnden Text ein: ";
    	getline(cin, text);
    
    	cout << "Bitte geben Sie die Anzahl Verschiebepositionen ein (als positive ganze Zahl): ";
    	cin >> v;
    	v %= 26;
    	for (int i = 0; i < text.length(); i++) {
    
    		if(text[i] >= 65 && text[i] <= 90) {
    
    			geheim += static_cast<unsigned>(text[i]) + v;
    
    			if (static_cast<unsigned>(geheim[i]) > 'Z') {
    				geheim[i] = static_cast<unsigned>(geheim[i]) - (v / 26 + 1) * 26;
    			}
    
    		}
    		else if (text[i] >= 97 && text[i] <= 122) {
    			geheim += static_cast<unsigned>(text[i]) + v;
    
    			if (static_cast<unsigned>(geheim[i]) > 'z') {
    				geheim[i] = static_cast<unsigned>(geheim[i]) - (v / 26 + 1) * 26;
    			}
    
    		}
    		else {
    			geheim += text[i];
    		}
    
    	}
    
    	cout << geheim << endl;
    	system("pause");
    
    }
    

    vielen Dank!



  • Wie ich oben schon schrob:
    Wenn Du

    v %= 26;
    

    machst, dann kann

    (v / 26 + 1) * 26;
    

    einfach durch

    26
    

    ersetzt werden, denn dann ist

    v / 26 + 1
    

    immer gleich 1.


Anmelden zum Antworten