Laboration
Under dessa fem laborationer kommer du att bygga upp ett Krypto-program med flera olika funktioner. Under laborationens gång
kommer det att ställas frågor, anteckna svaren på dessa. Du ska kunna redogöra för dem likväl som för den kod du skriver när
du redovisar. På sina ställen finns länkar i texten, dessa går ibland till Java´s API.
Det är ett jättebra ställe att titta på om man t.ex. inte riktigt vet hur en metod fungerar. Innan du sätter igång med Deluppgift 1
är det bra om du skummar igenom hela labblydelsen så att du ser vad som ska göras i de olika deluppgifterna (det finns 8 stycken totalt).
Deluppgift 1.
Skapa en meny som vid exekvering skrivs ut i terminalfönstret. Innehållet ska vara detsamma
som i exemplet nedan. Utgå gärna från kodexemplet.
Kodexempel: (sparas i en fil som heter Krypto.java
)
import java.io.*;
class Krypto{
public static void main(String args[]) throws IOException{
BufferedReader indata = new BufferedReader(
new InputStreamReader(
System.in));
//här kan utskrift till terminalfönster ske.
}//main()
}//Krypto
Exekveringsexempel:
1. Kryptera Caesarrullning
2. Dekryptera Caesarrullning
3. Forcera Caesarrullning
Gör ditt val (1,2 eller 3):
Tips:
-
Utskrift till terminalfönstret görs med
System.out.print()
Frågor:
-
Vad är det för skillnad på
System.out.print()
och System.out.println()
?
-
Vilken datatyp är det som skrivs ut i terminalfönstret?
-
Ge exempel på tre andra datatyper i Java.
Deluppgift 2.
Läs in det val användare gör i menyn och gör om det till ett heltal.
Tips:
-
Inläsning från terminalfönstret kan göras genom att skriva
-
Genom att använda kan man göra om objekt av datatypen sträng till heltal.
Frågor:
-
Vad är en variabel?
-
Vad är skillnaden på att initiera en variabel respektive att deklarera en variabel?
-
Vad händer om man skriver in någonting annat än ett heltal, t.ex. "Hej!"? Varför?
Deluppgift 3.
För att du ska ha någon nytta av att ha läst in vilket val användaren gjort måste du veta vad han/hon valde.
Lägg till ytterligare kod i main-metoden som avgör vad användaren har valt. Skriv ut valet i terminalfönstret för att
testa om koden blivit korrekt.
Tips:
-
If-, else- och if else-satser. Om du känner dig osäker på hur villkorssatser fungerar kan du kolla här.
Frågor:
- Vad skriver följande program ut?
...
int a=1;
int b=2;
int c=3;
if(a==b){
System.out.println("a="+a);
}
else if(a!=b){
System.out.println("b="+b);
}
else{
System.out.println("c="+c);
}
...
-
Givet följande deklarationer, vilka värden har följande booleska uttryck? Om du vill kan du skriva ett program som
skriver ut alla uttryck, ex.
System.out.println(c==(a==b));
, för att verifiera era svar.
int a=10, b=20;
boolean c=true, d=false;
1. c==(a==b)
2. c==(a<b)
3. (a==b)==(a==b+10)
4. (a==0)==(b==0)
5. (a<=15)==(b>=25)
6. (c==(a<b))==d
Deluppgift 4.
Caesarrullning är ett enkelt substitutionskrypto
som i korthet fungerar så här. Givet ett meddelande M och ett tal n byts varje bokstav i meddelandet M ut mot
bokstaven n steg framåt i alfabetet. Om n=3 byts a mot d, b mot e osv. I den variant av Caesarrullning du ska implementera
ska mellanslag och skiljetecken behållas okrypterade. Vidare kan du anta att inga meddelanden innehåller 'å', 'ä' eller 'ö'. När meddelandet har nått sin mottagare, som
givetvis känner till talet n, byter han eller hon tillbaka den krypterade bokstaven mot bokstaven n platser före i alfabetet.
Ett exempel är nog på sin plats: "legenden om zorro kan vara en myt, vad tror du?"
blir krypterat med n=3
"ohjhqghq rp cruur ndq ydud hq pbw, ydg wuru gx?"
Om man i menyn väljer Kryptera Caesarrullning
ska man bli presenterad för ytterligare två
alternativ. Dels ska användaren få mata in en mening som ska krypteras och dels ska användaren mata in heltalet n.
Exekveringsexempel:
1. Kryptera Caesarrullning
2. Dekryptera Caesarrullning
3. Forcera Caesarrullning
Gör ditt val (1,2 eller 3): 1
Ange mening som ska krypteras: legenden om zorro kan vara en myt, vad tror du?
Ange n: 3
Skapa en metod public static String caesar(String m, int n){return "";}
utanför main men i klassen Krypto
som tills vidare inte uträttar någonting. Skriv också ett anrop från main till metoden med de inlästa värdena som argument.
Kontrollera att metod samt anrop fungerar genom att exempelvis göra någon lämplig utskrift till terminalfönstret.
Tips:
Frågor:
-
Nämn en fördel med att använda sig av metoder när man programmerar Java.
-
Vad är skillnaden mellan formella parametrar och argument?
-
Vad är skillnaden mellan dessa två anrop till metoden caesar?
-
caesar("hej",3);
-
String s = caesar("hej",3);
-
Vad menas med returtyp och var anges den?
-
Vad skulle hända om det inte står
return "";
i er caesarmetod? Varför då?
Deluppgift 5
Nu är det dags att få din caesarmetod att göra någonting. Skriv ned (på papper) en relativt detaljerad algoritm för hur metoden ska
lösa problemet. Implementera algoritmen. Testa om den fungerar genom att skriva ut svaret från anropet caesar("zebra",3);
Blev det "cheud"?
Tips:
- När man vill iterera (loopa) över ett känt antal element, exempelvis alla bokstäver i alfabetet eller antalet tecken i en sträng är
det ofta en bra idé att använda sig av en for-slinga.
-
En array med bokstäver kan skapas så här:
char[] alfabet_inledning = {'a','b','c','d'};
och man kan
hämta saker ur arrayen genom att skriva char c = alfabet_inledning[1];
vilket i det här fallet skulle returnera bokstaven 'b'. Det första elementet i arrayen ligger alltså på plats 0.
-
Vid något tillfälle kommer du kanske att ha nytta av följande formel:
indexplats-26+n
.
Frågor:
-
Vad är en algoritm?
-
Vad är skillnaden mellan en for-slinga och en while-slinga?
-
Skulle du (eller någon annan) kunna skriva om koden som krypterar ett meddelande med Caesarrullningen med en (eller flera) whileslingor? Ja/nej svar räcker.
-
Om man istället för tecken skulle vilja lagra strängarna
"banan"
och "äpple"
eller heltalen mellan 1 och 5. Hur skulle deklarationen/initieringen av arrayen se ut då?
-
Hur skulle man kunna ändra koden så att den istället för att kryptera dekrypterar meddelandet?
Deluppgift 6.
Nu är det dags att utöka funktionaliteten i ditt program genom att erbjuda dekryptering också. Ge din caesarmetod ytterligare en formell
parameter, String alt
. Poängen med den är att man i anropet till caesarmetoden ska ange vad man vill göra. Ett anrop ska nu
kunna se ut så här caesar("hemligt",3,"k")
, där k står för kryptera. Skriv nu om din caesarmetod, ändra så lite som möjligt, så att
den fungerar som tidigare om villkoret alt.equals("k")
är uppfyllt och dekrypterar annars. Glöm inte bort
att ändra anropet om man valt alternativ 1 från menyn samt erbjud användaren samma alternativ (ange mening och heltalet n) om man väljer alternativ 2.
Tips:
-
Vid något tillfälle kommer du kanske att ha nytta av följande formel:
indexplats+26-n
.
- Metoden skulle nu kunna likna nedanstående.
public static String caesar(String m, int n, String alt){
/* deklarering av lokala variabler */
/* gemensam kod oavsett alt */
if(alt.equals("k")){
/* Kryptera som tidigare */
}
else{
/* Dekryptera */
}
return "krypterad/dekrypterad text";
}
Frågor:
-
Inga frågor på denna deluppgift.
Deluppgift 7.
Utöver möjligheterna att kryptera och dekryptera ska du nu också erbjuda användarna av ditt kryptosystem att forcera Caesarrullning.
Med det menas att man ska få fram klartexten utan att känna till n. Det finns olika sätt att göra detta. Ett är att prova alla
möjliga kombinationer (det finns ju bara 26 olika) och se vilken som resulterar i en begriplig mening. Det sättet vi ska använda oss av här
fungerar även på andra typer av substitutionskrypton än Caesarrullning och heter frekvensanalys, om än en något förenklad variant.
Den förenklade varianten fungerar så här: Utifrån att man vet att bokstaven 'e' är den vanligaste bokstaven i svenska språket (och engelska) kan
man räkna vilken bokstav som är vanligast i sin kryptotext och därmed veta att den ska bytas mot 'e'. Om man också räknar på vilket avstånd den ligger från 'e' i alfabetet
kan man nu göra samma sak för alla andra bokstäver genom att byta mot motsvarande bokstav på samma avstånd i alfabetet.
Exempel: topphemligt meddelande till chefen
blir Caesarkrypterat (med n=3, men det vet du ju inte.) wrsskhpoljw phgghodqgh wloo fkhihq
. I den texten finns det flest av
bokstaven 'h'. I kryptotexten ska alltså alla 'h' ersättas med 'e'. Om 'h' ska bytas ut mot 'e', som ligger på avstånd tre ifrån varandra i alfabetet, måste alla andra bokstäver också bytas mot den tre platser före i alfabetet.
Detta är helt logiskt med tanke på att den som krypterat meddelandet valde n=3 vid krypteringen.
Tips:
-
Läs mer om frekvensanalys på länken ovan om du är intresserade.
Frågor:
-
Har du förstått den förenklade varianten av frekvensanalys?
-
Vad händer om man kommer över en väldigt kort text och försöker forcera den?
Deluppgift 8.
För att dela upp program i flera fristående delar och därmed ha bättre kontroll och översikt över koden skapar man i Java
klasser. En klass kan beskriva en textsträng, vektor eller mer komplicerade objekt som olika grafiska element. Man kommunicerar med
dessa objekt via metoder, ex. text.length()
där text är ett objekt av typen sträng och length är en metod som
returnerar strängens längd. Vilka metoder som är tillgängliga bestäms, såklart, av vilken typ av objekt det är.
Din uppgift nu är att skapa en klass så att metoden forcera här nedanför fungerar och ger önskvärt resultat.
Använd gärna koden nedan till dels menyn (om man tryckt '3') och dels forcera-metoden.
Kod till menyn:
System.out.print("Ange krypterat meddelande som du vill försöka forcera: ");
String m = indata.readLine();
String nytt_med = forcera(m);
System.out.println("Meddelandet är antagligen: "+nytt_med);
Den nya metoden:
public static String forcera(String s){
Frekvensanalys fa = new Frekvensanalys(s);
fa.raknaForekomster();
fa.bestamVanligasteOchAvstand();
fa.skapaKlartext();
return fa.visaKlartext();
}
Tips:
Frågor:
-
Vad är skillnaden mellan en klass och en instans?
-
Hur ser koden ut om man vill anropa instansmetoden vikt hos kalle som är en instans av klassen människa?
-
Forcera meddelandet.
jizhfynts nx bmfy wjrfnsx bmjs tsj mfx ktwltyyjs jajwdymnsl mj qjfwsji ns xhmttq. - fqgjwy jnsxyjns