erstellt 24.01.99; überarbeitet 31.07.07, 20.0.08; übersetzt 13.11.12, überarbeitet 06.12.23, 20.02.24, 28.1.25; deutsche Übersetzung Heinrich Gailer
Es ist Frühling und wir planen 10 Tomatensetzlinge einzupflanzen. Die Wahrscheinlichkeit, dass eine einzelne Pflanze überlebt ist 90%. Wie viele der 10 Pflanzen werden überleben?
Wir schreiben ein Programm, dass das simuliert. Wir brauchen eine Schleife mit 10 Loops (einen pro Pflanze). Für jede Pflanze werfen wir einen 10-seitigen Würfel. Wenn die gewürfelte Zahl zwischen 1 und 9 liegt, wird die Pflanze überleben.
Natürlich werden mehrere Programmdurchläufe unterschiedliche Ergebnisse produzieren. Wir starten das Programm ein paar Mal und kalkulieren die durchschnittliche Anzahl der Pflanzen, die die Saison überleben. Oder noch besser wir schreiben ein Programm, das den Durchschnitt der überlebenden Pflanzen für 100 simulierte Jahreszeiten berechnet.
Wir schreiben ein Programm, dass ein Ratespiel implementiert. Das ist ein "klassisches" Programm, das häufig in den Anfangsklassen der Informatik gestellt wird.
Das Programm ermittelt eine Zufallszahl zwischen 1 und 10. Der Anwender bekommt jetzt 3 Versuche die Zahl zu erraten. Sobald der Anwender die richtige Zahl eingibt, gibt das Programm eine Gewinnmeldung aus und endet. Wenn der Anwender nach 3 Versuchen die richtige Zahl nicht erraten hat, gibt das Programm eine entsprechende Meldung aus und endet.
Wir verwenden die Methoden der Klasse Random
.
Hier sind zwei Probeläufe des Programms:
D:\>java Ratespiel Ich denke an eine Zahl von 1 bis 10. Sie haben 3 Versuche diese Zahl zu erraten. Raten Sie: Versuch: 1 2 Falsch Versuch: 2 4 Falsch Versuch: 3 7 Falsch Die richtige Zahl war 9. Sie haben das Spiel verloren. D:\>java Ratespiel Ich denke an eine Zahl von 1 bis 10. Sie haben 3 Versuche diese Zahl zu erraten. Raten Sie: Versuch: 1 3 Falsch Versuch: 2 5 RICHTIG! Sie haben das Spiel gewonnen.
Zurück zum Inhaltsverzeichnis.
Wir schreiben ein etwas komplizierteres Ratespiel. Das Programm ähnelt der Aufgabe 1, aber jetzt soll das Programm zusätzlich das Folgende ausgeben:
von der korrekten Antwort entfernt ist. Sobald der Anwender die richtige Zahl eingibt gibt das Programm eine Gewinnmeldung aus und endet:
D:\>java Ratespiel2 Ich denke an eine Zahl von 1 bis 10. Sie haben 3 Versuche diese Zahl zu erraten. Raten Sie: 1 kalt 5 RICHTIG! Sie haben das Spiel gewonnen. D:\>java Ratespiel2 Ich denke an eine Zahl von 1 bis 10. Sie haben 3 Versuche diese Zahl zu erraten. Raten Sie: 4 kalt 5 kalt 8 falsch Die richtige Zahl war 9. Sie haben das Spiel verloren. D:\>java Ratespiel2 Ich denke an eine Zahl von 1 bis 10. Sie haben 3 Versuche diese Zahl zu erraten. Raten Sie: 4 hot 5 warm 3 RICHTIG! Sie haben das Spiel gewonnen.
Die Methode Math.abs()
könnte hier nützlich sein.
Zurück zum Inhaltsverzeichnis.
Wir schreiben eine noch bessere Version. Jetzt besteht das Spiel aus 10 "Runden", wobei jede Runde aus einem Spiel wie bei Aufgabe 2 besteht. Nach den 10 Runden gibt das Programm aus wie viele Runden gewonnen und wie viele verloren wurden.
Hier ist ein Probelauf:
D:\>java Ratespiel3 Runde 1: Ich denke an eine Zahl von 1 bis 10. Sie haben 3 Versuche diese Zahl zu erraten. Raten Sie: 4 hot 5 RICHTIG! Sie haben 1 von 1 Runde(n) gewonnen. Runde 2: Ich denke an eine Zahl von 1 bis 10. Sie haben 3 Versuche diese Zahl zu erraten. Raten Sie: 10 kalt 5 kalt 3 falsch Die richtige Zahl war 1. Sie haben 1 von 2 Runde(n) gewonnen. . . . Runde 10: Ich denke an eine Zahl von 1 bis 10. Sie haben 3 Versuche diese Zahl zu erraten. Raten Sie: 1 kalt 6 warm 8 RICHTIG! Sie haben 7 von 10 Runde(n) gewonnen. Ihre Bewertung: Amateur. D:\>
Zurück zum Inhaltsverzeichnis.
Diese Aufgabe basiert auf dem Programm PasswortGenerator
in diesem Kapitel.
Um das Passwort zu verbessern editieren wir die Zeichenkette in auswahl
,
so dass sie mehr Ziffern enthält und erhöhen damit die Chancen, dass Ziffern ausgewählt werden.
Wir tun das, indem wir einige Male "1234567890" an das Ende von auswahl
anhängen.
Es gibt keinen Grund warum auswahl
nicht einzelne Zeichen mehrmals enthalten kann.
Wenn wir Satzzeichen für die Passwörter haben wollten, können wir sie ebenfalls anhängen.
Eine weitere Verbesserung ist, dass ein Passwort mindestens 1 Ziffer enthalten muss. Es gibt mehrere Möglichkeiten das umzusetzen. Wir setzen nicht voraus, dass die erforderliche Ziffer in einem Passwort an einer festen Stelle steht.
Eine weitere Verbesserung ist die Regel, dass auf jeden Konsonanten ein Vokal folgen muss in der gleichen Groß- oder Kleinschreibung. Das macht das Passwort leichter merkbar. Natürlich kann es dann auch leichter erraten werden, besonders wenn ein Hacker weiss das diese Regel verwendet wird.
Zurück zum Inhaltsverzeichnis.
Ein Passwort Generator kann auch als ein Passwort Cracker verwendet werden. Im Wesentlichen erzeugt dieser Generator Passwörter bis er eines findet, das funktioniert. (Das ist der Grund warum viele Applikationen ein Login nach dreimaliger Falscheingabe verweigern.)
Wir schreiben ein Programm, das den Anwender nach einem Passwort fragt. Der Anwender gibt ein Passwort ein (das kurz sein muss). Jetzt tun wir so, als ob das Passwort dem Rest des Programms nicht bekannt ist. Das Programm verwendet dann wiederholt den Passwort Generator bis ein zufällig erzeugtes Passwort mit dem vom Anwender eingegebenen Passwort übereinstimmt. Wir setzen voraus, dass das eingegebene Passwort aus 5 Zeichen oder weniger besteht (andererseits wird das Programm niemals enden). Das Programm gibt die Anzahl der Versuche um das Passwort zu finden aus. Hier sind ein paar Programmläufe:
D:\cai\>java PasswortCracker Geben Sie ein "geheimes" Passwort ein:ant Hier ist Ihr Passwort: ant Es brauchte 2181892 Versuche um es zu raten D:\cai\>java PasswortCracker Geben Sie ein "geheimes" Passwort ein:rats Hier ist Ihr Passwort: rats Es brauchte 10956100 Versuche um es zu raten D:\cai\>java PasswortCracker Geben Sie ein "geheimes" Passwort ein:frog Hier ist Ihr Passwort: frog Es brauchte 91555945 Versuche um es zu raten D:\cai\>java Passwor7Cracker Geben Sie ein "geheimes" Passwort ein:moose Hier ist Ihr Passwort: moose Es brauchte 279530402 Versuche um es zu raten
Ein besseres Cracker Programm würde systematisch alle möglichen ein-buchstabigen, dann alle möglichen zwei-buchstabigen, dann alle möglichen drei-buchstabigen Passwörter usw. erzeugen. Aber dieses Programm wäre nur sehr schwer ohne Arrays zu schreiben (die in einem späteren Kapitel besprochen werden).
Zurück zum Inhaltsverzeichnis.
Der Durchschnitt von 1000 Ganzzahlen von 0 bis 100 ist 500. Die ganzen Zahlen 0 bis 499 liegen auf der einen Seite von 500 und die ganzen Zahlen 501 bis 1000 sind auf der anderen Seite. Der Durchschnitt einer Stichprobe von ganzen Zahlen, die zufällig aus dem Bereich [0,1000] ausgewählt wurden, sollte also etwa 500 betragen.
Wir schreiben ein Programm, das den Benutzer nach der Anzahl der Zahlen, N
fragt und dann den Durchschnitt von N
zufällig ausgewählten Integern aus dem Bereich von [0,1000] berechnet.
Beachtet, dass sowohl die 0 als auch Tausend in dem Bereich enthalten sind. Wir berechnen den Durchschnitt als double
-Wert. Natürlich werden wir jedes Mal, wenn wir das Programm für die gleiche Anzahl N
ausführen, höchstwahrscheinlich ein anderes Ergebnis erhalten.
Wir führen das Programm für verschiedene Werte von N
aus (und zwar mehrere Male für jedes N
) und beobachten, wie nahe die Werte bei 500 liegen. Random
kann die gleichen Werte mehr als einmal erzeugen, so dass sogar wenn N
1000 ist, der Durchschnitt nicht genau 500 betragen wird.
Zurück zum Inhaltsverzeichnis.
Eine zufällige Bewegung in einem eindimensionalem Raum ist wo ein Teilchen bei x=0.0 startet und sich dann rechts oder links entlang der x-Achse zufällig bewegt. Beachtet, dass x negativ oder positiv (oder 0) sein kann. Stellt Euch eine Perle aufgefädelt an einer gespannten Schnur vor, die zufällig ihre Position innerhalb einer bestimmten Spanne ändert. Sie bewegt sich zufällig mal links, mal rechts, zufällig mal mehr, mal weniger.
Wir schreiben ein Programm, dass eine Variable x=0
initialisiert,
die die Position der Perle repräsentiert. Dann werden x
zufällige Beträge im
Bereich (-1.0, +1.0) hinzugefügt.
Das Programm endet nach einer bestimmten Anzahl von Iterationen.
Wir werden die Methode nextDouble()
von Random
brauchen.
Sie muss anpasst werden, um mit dem spezifizierten Bereich übereinzustimmen.
Wie weit entfernt von der Startposition ist x
nach 100 Iterationen? 1000 Iterationen?
Welche maximale Entfernung ist möglich) und wie wahrscheinlich ist das?
D:\cai\>java RandomWalkOneDim Wie viele Iterationen? 100 Nach 100 Bewegungen ist x jetzt bei 1.1190381131949723 D:\cai\>java RandomWalkOneDim Wie viele Iterationen? 1000 Nach 1000 Bewegungen ist x jetzt bei -0.4633309201402265
Wir ändern das Programm so, dass es so lange wiederholt wird, bis die Perle einen bestimmten Abstand (positiv oder negativ) vom Ursprung erreicht. Wir verwenden Math.abs()
, um den Abstand zu bestimmen. Wenn Ihr einen großen Abstand wählt, kann es sein, dass Ihr das laufende Programm stoppen müsst, da der Abstand möglicherweise nie erreicht wird. (Auf Windows Systemen könnt Ihr das Programm mit Control-C im DOS-Fenster beenden).
Zurück zum Inhaltsverzeichnis.
Bei einem zweidimensionalen Random Walk beginnt ein Teilchen bei X=0,0, Y=0,0 und bewegt sich dann in kleinen zufälligen Schritten in X und Y. Wir stellen uns eine verwirrte Ameise vor, die sich zufällig in einem zweidimensionalen Raum bewegt.
Wir schreiben ein Programm, das zwei Variablen X
und Y
, die die Position der Ameise darstellen, mit 0 initialisiert und dann wiederholt zufällige Werte im Bereich (-1.0, +1.0) zu jeder dieser Variablen addiert.
Wir wählen zwei zufällige Werte, einen für X
und einen für Y
. Das Programm endet nach einer bestimmten Anzahl von Iterationen und gibt die Werte der Koordinaten und den endgültigen Abstand der Ameise vom Ursprung aus. Wir verwenden die Formel von Pythagoras, um den Abstand zu berechnen:
_______ distance = \/X2 + Y2
Für dieses Programm sind viele Variationen möglich. Zum Beispiel das Zählen der Schritte, die nötig sind, um eine bestimmte Entfernung zu erreichen. Oder man implementiert zwei Ameisen, jede mit ihren eigenen Koordinaten, die beide bei (0, 0) beginnen und 1000 Schritte wandern. Wie weit sind die Ameisen voneinander entfernt? Wenn sich eine Ameise nicht bewegt, sind sie dann näher oder weiter voneinander entfernt, als wenn sie sich beide bewegen?
Natürlich, eine andere Variante wäre die Implementierung eines 3D Zufallslaufs mit den unabhängigen Variablen X, Y und Z. Wir stellen uns z.B. ein verwirrtes Glühwürmchen vor, das zufällig durch die Nacht flattert.
Zurück zum Inhaltsverzeichnis.
Wir schreiben ein Programm, das ein Spiel für zwei Spieler implementiert. Der Computer ist der Punktezähler und die beiden Spieler sind Menschen. Jede Spielrunde beginnt damit, dass der Computer zufällig eine Zahl mit doppelter Genauigkeit zwischen 1,0 und etwas weniger als 100,0 auswählt. Jeder Spieler schätzt die Quadratwurzel der Zahl und gibt die Schätzung ein. Der Spieler, dessen Schätzung der richtigen Zahl am nächsten kommt, gewinnt die Runde. Die Spieler wechseln sich ab, wer in jeder Runde den Anfang macht. Das Spiel endet nach einer bestimmten Anzahl von Runden.
Wie viele Runden? 4 Name erster Spieler--> Dweezle Name zweiter Spieler--> Moon Unit Wie lautet die Quadratwurzel von 83.29097831183603 ? Dweezle schaetzt: 9.1 Moon Unit schaetzt: 9.2 Die richtige Quadratwurzel ist: 9.126389116832353 Dweezle ist 0.026389116832353565 entfernt Moon Unit ist 0.07361088316764608 entfernt Dweezle gewinnt! Was ist die Quadratwurzel aus 87.79346957866132 ? Moon Unit schaetzt: 8.8 Dweezle schaetzt: 8.9 Die richtige Quadratwurzel ist: 9.36981694477866 Dweezle ist 0.46981694477866043 entfernt Moon Unit ist 0.5698169447786601 entfernt Dweezle gewinnt! Was ist die Quadratwurzel aus 67.44682032701256 ? Dweezle schaetzt: 8.2 Moon Unit schaetzt: 8.1 Die richtige Quadratwurzel ist: 8.212601313044033 Dweezle ist 0.012601313044033446 entfernt Moon Unit ist 0.11260131304403309 entfernt Dweezle gewinnt! Was ist die Quadratwurzel aus 71.64725527288849 ? Moon Unit schaetzt: 8.4 Dweezle schaetzt: 8.45 Die richtige Quadratwurzel: 8.464470170831042 Dweezle ist 0.01447017083104285 entfernt Moon Unit ist 0.06447017083104178 entfernt Dweezle gewinnt! ---- Endergebnis ---- Dweezle: 4 Moon Unit: 0
Wir rufen nach der Anzahl der Iterationen die Methode nextLine()
von Scanner
auf, um das Zeilen Endezeichen einzulesen. Danach werden die Spielernamen mit nextLine()
eingelesen. Wir verwenden nextDouble()
für die Schätzungen. Math.abs()
und Math.sqrt()
werden nützlich sein.
Zurück zum Inhaltsverzeichnis.
Das ist ein Würfelspiel ähnlich dem Spiel Pig (auch als Böse Eins bekannt), aber einfacher zu implementieren. Der Spieler spielt gegen den Computer.
In einem echten Pig-Spiel würde der Computer wiederholt einen einzelnen Würfel werfen (genau wie der Spieler) und mit Hilfe einer Strategie bestimmen, wann er aufhört.
Zurück zum Inhaltsverzeichnis.