Kompilieren und ausführen
Speichere das Programm als CaesarCipher.java, denn der Dateiname muss zum Klassennamen passen. Führe dann im selben Ordner diese beiden Befehle aus:
javac CaesarCipher.javajava CaesarCipherDer erste kompiliert den Code, der zweite startet ihn und gibt den verschlüsselten Text aus. Ist die Chiffre selbst noch neu für dich, hilft die Anleitung ganz ohne Code.
So funktioniert der Code
In Java ist ein char zugleich eine Zahl, du kannst also direkt damit rechnen: 'H' - 'A' ergibt 7, die Position im Alphabet. Nach dem Addieren der Verschiebung hält Math.floorMod das Ergebnis zwischen 0 und 25, deshalb landet Z bei der Verschiebung 3 auf C.
base + index liefert einen int, darum steht davor der Cast (char). Das Ergebnis sammelt ein StringBuilder, weil jedes Anhängen an einen String in der Schleife ein neues Objekt erzeugt.
Leerzeichen, Satzzeichen und Ziffern laufen unverändert durch den else-Zweig. Die Prüfung c < 128 ist nötig, weil Character.isLetter auch ä, ö und ü akzeptiert. Ohne sie würden Umlaute zu irgendeinem Buchstaben von A bis Z, und der Text ließe sich nicht mehr korrekt entschlüsseln.
Entschlüsseln in Java
Eine zweite Methode brauchst du nicht. Entschlüsseln ist dieselbe Verschiebung in die andere Richtung, also übergibst du eine negative Zahl:
System.out.println(caesar("Kdoor Zhow!", -3));// Hallo Welt!Genau deshalb nutzt der Code Math.floorMod. Der Operator % behält in Java das Vorzeichen der linken Zahl, -3 % 26 ergibt also -3, und das ist gar kein Buchstabe. Math.floorMod(-3, 26) liefert 23, und A geht zurück zu X. In der Python-Version verhält sich schon % so.
Eingabe mit Scanner
Oft verlangt eine Aufgabe, dass das Programm Text und Verschiebung über die Tastatur einliest. Setz den Import ganz oben in die Datei und ersetze main durch diesen Code:
import java.util.Scanner; public static void main(String[] args) { Scanner scanner = new Scanner(System.in); System.out.print("Text: "); String text = scanner.nextLine(); System.out.print("Verschiebung: "); int shift = scanner.nextInt(); System.out.println(caesar(text, shift));}Lies zuerst den Text. nextInt() lässt das Zeilenende stehen, ein danach aufgerufenes nextLine() würde also einen leeren String liefern.
Die Chiffre mit Brute Force knacken
Bei 26 Buchstaben gibt es nur 25 Verschiebungen zum Ausprobieren, also liest eine kurze Schleife die Nachricht auch ohne Schlüssel. Du musst nur die Zeile finden, die einen Sinn ergibt:
public static void crack(String text) { for (int shift = 1; shift < 26; shift++) { System.out.println(shift + " " + caesar(text, -shift)); }} public static void main(String[] args) { crack("Kdoor Zhow!"); // 1 Jcnnq Ygnv! // 2 Ibmmp Xfmu! // 3 Hallo Welt! // ...}Mehr dazu steht im Artikel über den Brute-Force-Angriff, und der Caesar-Knacker erledigt dasselbe im Browser.
Caesar mit Umlauten und ß
Sollen auch ä, ö, ü und ß verschoben werden, legst du das Alphabet als String ab und suchst jedes Zeichen mit indexOf(). Das sind dieselben 30 Zeichen wie in unserem Tool:
static final String ALPHABET = "aäbcdefghijklmnoöpqrstuüvwxyzß"; public static String caesarAlphabet(String text, int shift) { StringBuilder result = new StringBuilder(); for (char c : text.toCharArray()) { int position = ALPHABET.indexOf(Character.toLowerCase(c)); if (position == -1) { result.append(c); } else { int index = Math.floorMod(position + shift, ALPHABET.length()); char next = ALPHABET.charAt(index); result.append(Character.isUpperCase(c) ? Character.toUpperCase(next) : next); } } return result.toString();} public static void main(String[] args) { System.out.println(caesarAlphabet("Schöne Grüße", 3)); // Üfkrph Juxbh}Der Umlauf nutzt jetzt ALPHABET.length(), die 30 musst du also nirgends eintragen. Character.toUpperCase('ß') lässt das ß übrigens unverändert, die Zeichenzahl bleibt also gleich. Vergleichen kannst du das Ergebnis im Caesar-Tool mit dem deutschen Alphabet.
Eine Textdatei verschlüsseln
Files.readString und Files.writeString lesen und schreiben eine ganze Datei in einer Zeile, standardmäßig in UTF-8, sodass Umlaute erhalten bleiben. Dabei kann ein Fehler auftreten, darum braucht main ein throws IOException.
import java.io.IOException;import java.nio.file.Files;import java.nio.file.Path; public static void main(String[] args) throws IOException { String text = Files.readString(Path.of("message.txt")); Files.writeString(Path.of("encrypted.txt"), caesar(text, 3));}Den Code testen
Mit diesen Zeilen in main findest du die typischen Fehler. Java ignoriert assert, solange du es nicht einschaltest, starte das Programm also mit java -ea CaesarCipher. Ist alles in Ordnung, gibt es OK aus.
assert caesar("ABC", 3).equals("DEF");assert caesar("xyz", 3).equals("abc");assert caesar("Hello, World!", 5).equals("Mjqqt, Btwqi!");assert caesar(caesar("Java", 7), -7).equals("Java");assert caesar("A", 26).equals("A");assert caesar("é", 3).equals("é");System.out.println("OK");Häufige Fehler
Am häufigsten ist % bei negativer Verschiebung, wie oben beschrieben. Ebenfalls beliebt ist der fehlende Cast: result.append(base + index) hängt die Zahl 75 an, wo du den Buchstaben K wolltest. Und vergleiche Strings in Tests mit equals(), denn == prüft nur, ob es dasselbe Objekt ist.
Häufige Fragen
Welche Java-Version brauche ich?
Das Hauptprogramm läuft ab Java 8. Das Datei-Beispiel braucht Java 11, denn seitdem gibt es Files.readString. Wir haben den Code dieser Seite mit Java 21 kompiliert und ausgeführt.
Kann ich damit echte Daten schützen?
Nein. Die Schleife von oben knackt die Chiffre in Sekunden. Nimm sie zum Lernen und für Rätsel. Für echte Daten bringt Java moderne Verschlüsselung wie AES im Paket javax.crypto mit.
Wie prüfe ich, ob mein Ergebnis stimmt?
Gib denselben Text und dieselbe Verschiebung in unser Caesar-Tool ein und vergleiche. Aus deinen Tests heraus kannst du auch die kostenlose REST-API aufrufen.