html5-img
1 / 76

Übungen zur objektorientierten Programmierung

Übungen zur objektorientierten Programmierung. Klaus Becker 2013. Objektorientierung. "Objektorientierung ist die derzeitige Antwort auf die gestiegene Komplexität der Softwareentwicklung." Oestereich: Objektorientierte Software-Entwicklung.

kareem
Download Presentation

Übungen zur objektorientierten Programmierung

An Image/Link below is provided (as is) to download presentation Download Policy: Content on the Website is provided to you AS IS for your information and personal use and may not be sold / licensed / shared on other websites without getting consent from its author. Content is provided to you AS IS for your information and personal use only. Download presentation by click this link. While downloading, if for some reason you are not able to download a presentation, the publisher may have deleted the file from their server. During download, if you can't get a presentation, the file might be deleted by the publisher.

E N D

Presentation Transcript


  1. Übungen zur objektorientierten Programmierung Klaus Becker 2013

  2. Objektorientierung "Objektorientierung ist die derzeitige Antwort auf die gestiegene Komplexität der Softwareentwicklung." Oestereich: Objektorientierte Software-Entwicklung Bei den hier zusammengestellten Übungen zur objektorientierten Programmierung geht es um einfache Spiele, die man am Computer ausführen kann. Ziel ist es, solche Spielprogramme mit Hilfe von Softwarebausteinen zu entwickeln.

  3. Teil 1 Objekte und Klassen

  4. Das Spiel 17-und-4 Ziel ist es, das Spiel 17-und-4 mit Hilfe geeigneter Softwarebausteine zu simulieren. Wir spielen 17-und-4 hier in einer vereifachten Version. Man benötigt hierzu einen Kartenstapel, bei dem die Karten gut durchmischt sind. Die Spieler können jetzt (reihum) Karten ziehen. Ziel ist es, mit den gezogenen Karten der Zahl 21 - also 17 und 4 - möglichst nahe zu kommen. Wer mit den gezogenen Karten mehr als 21 erzielt, hat allerdings verloren. Jede Karte hat dabei einen festgelegten Kartenwert: 11 10 9 8 7 4 3 2

  5. Kartenstapel Was macht einen Kartenstapel aus? mischen Karte ziehen ist leer? vorhandene Karten gezogene Karte Ein Kartenstapel besteht aus einer Ansammlung noch vorhandener Karten und ggf. einer gezogenen Karte. Einen Kartenstapel kann man mischen. Wenn er nicht leer ist, dann kann man die oberste Karte ziehen.

  6. Ein Bauplan für Kartenstapel-Objekte from random import randint class Kartenstapel(object): def __init__(self): self.kartenListe = [ 'X-A', 'X-K', 'X-D', 'X-B', 'X-10', 'X-9', 'X-8', 'X-7', 'P-A', 'P-K', 'P-D', 'P-B', 'P-10', 'P-9', 'P-8', 'P-7', 'H-A', 'H-K', 'H-D', 'H-B', 'H-10', 'H-9', 'H-8', 'H-7', 'K-A', 'K-K', 'K-D', 'K-B', 'K-10', 'K-9', 'K-8', 'K-7' ] self.gezogeneKarte = None def alleKartenAuflegen(self): self.kartenListe = [ 'X-A', 'X-K', 'X-D', 'X-B', 'X-10', 'X-9', 'X-8', 'X-7', 'P-A', 'P-K', 'P-D', 'P-B', 'P-10', 'P-9', 'P-8', 'P-7', 'H-A', 'H-K', 'H-D', 'H-B', 'H-10', 'H-9', 'H-8', 'H-7', 'K-A', 'K-K', 'K-D', 'K-B', 'K-10', 'K-9', 'K-8', 'K-7' ] self.gezogeneKarte = None def mischen(self): neueListe = [] aktuelleAnzahl = len(self.kartenListe) while aktuelleAnzahl > 0: i = randint(0, aktuelleAnzahl-1) neueListe = neueListe + [self.kartenListe[i]] del self.kartenListe[i] aktuelleAnzahl = len(self.kartenListe) self.kartenListe = neueListe ... mischen Karte ziehen ist leer? vorhandene Karten gezogene Karte

  7. Aufgabe 1 Auf I:1.10.2.1.2 findest du eine Implementierung der Klasse Kartenstapel. Führe einen Python-Dialog zu einem 17-und-4-Spiel (mit einem einzigen Spieler). Erzeuge hierzu zunächst ein Objekt der Klasse Kartenstapel. Benutze anschließend passende Methoden. Inspiziere nach jedem Schritt den Objektzustand. >>> >>> kartenstapel = Kartenstapel() >>> kartenstapel.kartenListe ['X-A', 'X-K', 'X-D', 'X-B', 'X-10', 'X-9', 'X-8', 'X-7', 'P-A', 'P-K', 'P-D', 'P-B', 'P-10', 'P-9', 'P-8', 'P-7', 'H-A', 'H-K', 'H-D', 'H-B', 'H-10', 'H-9', 'H-8', 'H-7', 'K-A', 'K-K', 'K-D', 'K-B', 'K-10', 'K-9', 'K-8', 'K-7'] ...

  8. Aufgabe 2 Die Verwendung eines Kartenstapel-Objekts kann man auch mit einem Testprogramm erkunden. (a) Speichere das folgende Testprogramm im selben Ordner ab, in dem auch eine Datei spielkarten.py mit der Klassendeklaration der Klasse Kartenstapel gespeichert ist. Führe das Testprogramm anschließend aus und erläutere die erzeugten Ausgaben. (b) Entwickle analog ein Testprogramm, das einen Kartenstapel erzeugt, die Karten mischt und anschließend solange die oberste Karte zieht und ausgibt, bis der Kartenstapel leer ist. Benutze dabei die in der Klassendeklaration vorgesehenen Operationen. from kartenspiel import Kartenstapel # Testprogramm kartenstapel = Kartenstapel() print(kartenstapel.kartenListe) print(kartenstapel.gezogeneKarte) print() kartenstapel.mischen() print(kartenstapel.kartenListe) print(kartenstapel.gezogeneKarte) print() print(kartenstapel.istLeer()) kartenstapel.karteZiehen() print(kartenstapel.kartenListe) print(kartenstapel.gezogeneKarte)

  9. Kartenhaufen Was macht einen einen Kartenhaufen aus? Karte hinzufügen Kartenliste Wert Unter einem Kartenhaufen soll hier eine Ansammlung von Karten verstanden werden. Einem solchen Kartenhaufen kann man weitere Karten hinzufügen. Ein Kartenhaufen hat zudem einen Gesamtwert (das ist die Summe der Werte aller Karten des Kartenhaufens). Im vorliegenden Beispiel beträgt der Gesamtwert 23.

  10. Aufgabe 3 class Kartenhaufen(object): def __init__(self): self.kartenListe = # ... self.wert = # ... def hinzufuegen(self, karte): self.kartenListe = # ... if karte[2] == 'A': kartenwert = 11 elif karte[2] == 'K': kartenwert = 4 # ... self.wert = # ... Die Klassendeklaration ist noch nicht ganz fertig. Kannst du die fehlenden Teile (mit #... markiert) ergänzen? Wenn du die Klassendeklaration richtig ergänzt hast, dann kannst du als Test einen geeigneten Python-Dialog führen. Vorher musst du die Klassendeklaration aber einmal ausführen, damit sie vom Python-Ausführsystem übernommen wird.

  11. Aufgabe 4 Speichere jetzt die Klassendeklarationen der Klassen Kartenstapel und Kartenhaufen in einer gemeinsamen Datei ab und führe sie einmal aus. Simuliere anschließend ein 17-und-4-Spiel mit zwei Spielern. Hier der Beginn einer solchen Simulation. >>> >>> >>> kartenstapel = Kartenstapel() >>> kartenstapel.mischen() >>> kartenhaufenSpieler1 = Kartenhaufen() >>> kartenhaufenSpieler2 = Kartenhaufen() >>> kartenstapel.karteZiehen() >>> karte = kartenstapel.gezogeneKarte >>> kartenhaufenSpieler1.hinzufuegen(karte) >>> kartenstapel.karteZiehen() >>> karte = kartenstapel.gezogeneKarte >>> kartenhaufenSpieler2.hinzufuegen(karte) >>> ...

  12. Aufgabe 5 In der Datei kartenspiel.py befinden sich die Deklarationen der Klassen Kartenstapel und Kartenhaufen. (a) Ein Spieler zieht seine Karten nach der folgenden Strategie: Solange der Gesamtwert aller Karten noch kleiner als 18 ist, wird eine Karte gezogen. Entwickle ein Simulationsprogramm zu dieser Strategie. (b) Ein Spieler zieht seine Karten immer nach der folgenden Strategie: Solange der Kartenwert noch kleiner als 18 ist, wird eine Karte gezogen. Ermittle mit einer Simulation, wie oft der Spieler bei dieser Strategie im Mittel über der 21 landet.

  13. Aufgabe 6 class Kartenhand(object): def __init__(self): self.kartenListe = [] self.anzahl = 0 def hinzufuegen(self, karte): self.kartenListe = self.kartenListe + [karte] self.anzahl = self.anzahl + 1 def wegnehmen(self, karte): if karte in self.kartenListe: i = self.kartenListe.index(karte) del self.kartenListe[i] self.anzahl = self.anzahl - 1 >>> >>> meineKarten = Kartenhand() >>> meineKarten.hinzufuegen('P-B') >>> meineKarten.kartenListe ? >>> meineKarten.hinzufuegen('H-10') >>> meineKarten.kartenListe ? >>> meineKarten.hinzufuegen('P-A') >>> meineKarten.kartenListe ? >>> meineKarten.wegnehmen('H-10') >>> meineKarten.kartenListe ? >>> meineKarten.wegnehmen('X-7') >>> meineKarten.kartenListe ? >>> meineKarten.anzahl ? (a) Analysiere zunächst die Klasse Kartenhand. Welche Attribute werden hier festgelegt? Was sollen sie verwalten? Welche Methoden gibt es? Was sollen sie leisten? Beschreibe die Klasse auch mit einem Klassendiagramm. (b) Was steht an Stelle der Fragezeichen? Überprüfe deine Vermutungen.

  14. Aufgabe 6 class Kartenhand(object): def __init__(self, kartenGegeben): self.kartenListe = kartenGegeben self.anzahl = len(self.kartenListe) def hinzufuegen(self, karte): self.kartenListe = self.kartenListe + [karte] self.anzahl = self.anzahl + 1 def wegnehmen(self, karte): if karte in self.kartenListe: i = self.kartenListe.index(karte) del self.kartenListe[i] self.anzahl = self.anzahl - 1 >>> >>> meineKarten = Kartenhand(['X-A', 'H-A', 'P-7']) >>> meineKarten.kartenListe ['X-A', 'H-A', 'P-7'] >>> meineKarten.anzahl 3 (c) Die Deklaration der Klasse Kartenhand unterscheidet sich von der oben gezeigten nur im Kontruktor. Was ist hier anders? Wozu könnte das gut sein? Betrachte hierzu auch den folgenden Python-Dialog.

  15. Aufgabe 6 class Kartenhand(object): def __init__(self, kartenGegeben): self.kartenListe = kartenGegeben self.anzahl = len(self.kartenListe) def existiertKarte(self, karte): if karte in self.kartenListe: ergebnis = True else: ergebnis = False return ergebnis def hinzufuegen(self, karte): if not self.existiertKarte(karte): self.kartenListe = self.kartenListe + [karte] self.anzahl = self.anzahl + 1 def wegnehmen(self, karte): if self.existiertKarte(karte): i = self.kartenListe.index(karte) del self.kartenListe[i] self.anzahl = self.anzahl - 1 (d) Erläutere die Unterschiede zu den bisher betrachteten Klassendeklarationen. Führe selbst einen Python-Dialog zum Testen aus. Dokumentiere mit diesem Dialog das Verhalten der einzelnen Methoden der Klasse.

  16. Aufgabe 7 Gegeben ist ein Klassendiagramm zur Beschreibung einer Klasse Wuerfel. (a) Erläutere die Bestandteile der Klasse Wuerfel: Welche Daten werden hier verwaltet? Welche Operationen soll ein Wuerfel-Objekt ausführen können? (b) Implementiere zunächst die Klasse Wuerfel. Entwickle dann einen Python-Dialog zum Testen dieser Klasse. In diesem Dialog sollen zwei Würfelobjekte erzeugt und geworfen werden. (c) Ermittle mit einem Testprogramm, wie oft man einen Würfel (durchschnittlich) werfen muss, bis die Summe der Augenzahlen der Würfelwürfe die Zahl 21 überschreitet. Benutze die Klasse Wuerfel, um ein Würfelobjekt zu erzeugen.

  17. Aufgabe 8 Für viele Spiele benötigt man eine Art Punktekonto. Auf dieses Konto kann man eine vorgegebene Anzahl von Punkten "einzahlen", der Punktekontostand erhöht sich dann entsprechen. Man kann analog auch eine vorgegebene Anzahl von Punkten "abheben", natürlich nur, wenn genügend Punkte auf den Konto sind. Entwickle zunächst ein Klassendiagramm mit allen benötigten Attributen und Methoden. Entwickle anschließend eine passende Implementierung und teste sie.

  18. Teil 2 Modularisierung

  19. Experimente mit Kartenhaufen-Objekten class Kartenhaufen(object): def __init__(self): self.kartenListe = [] self.wert = 0 def hinzufuegen(self, karte): self.kartenListe = self.kartenListe + [karte] if karte[2] == 'A': kartenwert = 11 elif karte[2] == 'K': kartenwert = 4 elif karte[2] == 'D': kartenwert = 3 elif karte[2] == 'B': kartenwert = 2 elif karte[2] == '1': kartenwert = 10 elif karte[2] == '9': kartenwert = 9 elif karte[2] == '8': kartenwert = 8 … self.wert = self.wert + kartenwert

  20. Aufgabe 9 >>> >>> meinKartenhaufen = Kartenhaufen() >>> meinKartenhaufen.hinzufuegen('K-B') >>> meinKartenhaufen.hinzufuegen('X-9') >>> meinKartenhaufen.kartenListe = meinKartenhaufen.kartenListe + ['H-K'] >>> meinKartenhaufen.kartenListe ['K-B', 'X-9', 'H-K'] >>> meinKartenhaufen.wert 11 (a) Welcher reale Vorgang wird hier simuliert? (b) Stimmt der angegebene Gesamtwert der Karten? Warum ist hier etwas schiefgelaufen?

  21. Aufgabe 10 >>> >>> meinKartenhaufen = Kartenhaufen() >>> meinKartenhaufen.hinzufuegen('K-B') >>> meinKartenhaufen.hinzufuegen('X-9') >>> meinKartenhaufen.hinzufuegen('H-K') >>> meinKartenhaufen.getKartenListe() ['K-B', 'X-9', 'H-K'] >>> meinKartenhaufen.getWert() 15 Ändere die Deklaration der Klasse Kartenhaufen passend zum Klassendiagramm ab.

  22. Aufgabe 11 class Kartenhand(object): def __init__(self, kartenGegeben): self.kartenListe = kartenGegeben self.anzahl = len(self.kartenListe) def existiertKarte(self, karte): if karte in self.kartenListe: ergebnis = True else: ergebnis = False return ergebnis def hinzufuegen(self, karte): if not self.existiertKarte(karte): self.kartenListe = self.kartenListe + [karte] self.anzahl = self.anzahl + 1 def wegnehmen(self, karte): if self.existiertKarte(karte): i = self.kartenListe.index(karte) del self.kartenListe[i] self.anzahl = self.anzahl - 1 Betrachte die Klasse Kartenhand. (a) Ergänze zunächst geeignete Zugriffsmethoden für die Attribute der Klasse. (b) Ergänze die Implementierung um eine Schnittstellenbeschreibung, so dass die Klasse benutzt werden kann, ohne dass man sich die Implementierungsdetails anschauen muss.

  23. Aufgabe 12 from random import randint class Lottogeraet(object): def __init__(self): # erzeugt e. Obj. z. Simulation e. Lottogeraets self.geraetVorbereiten() def geraetVorbereiten(self): # fuellt das Lottogeraet mit Kugeln von 1..49 # leert den Behaelter der gezogenen Kugeln self.vorhandeneKugeln = list(range(1, 50)) self.gezogeneKugeln = [] def kugelZiehen(self): # zieht ei. Kugel aus den noch vorhand. Kugeln # entfernt diese Kugel aus dem Kugelbehaelter # legt d. Kugel i. Behaelter d. gezog. Kugeln ab … Zur Simulation von Lotto-Ziehungen wird hier eine Klasse Lottogeraet bereitgestellt. Du findest eine Implementierung dieser Klasse in der Datei lotto.py (siehe I:1.10.2.2.8). (a) Teste die Klasse mit einem einfachen Testprogramm, das alle Methoden der Klasse benutzt. (b) Löse mit Hilfe der Klasse folgendes Problem: Wie oft kommt deine Lieblingszahl (z.B. die 13) in 1000 Lottoziehungen vor?

  24. Aufgabe 13 from random import randint class Lottogeraet(object): def __init__(self): # erzeugt e. Obj. z. Simulation e. Lottogeraets self.geraetVorbereiten() def geraetVorbereiten(self): # fuellt das Lottogeraet mit Kugeln von 1..49 # leert den Behaelter der gezogenen Kugeln self.vorhandeneKugeln = list(range(1, 50)) self.gezogeneKugeln = [] def kugelZiehen(self): # zieht ei. Kugel aus den noch vorhand. Kugeln # entfernt diese Kugel aus dem Kugelbehaelter # legt d. Kugel i. Behaelter d. gezog. Kugeln ab … Betrachte noch einmal die Klasse Lottogeraet zur Simulation eines Lottogeräts. Ziel ist es, die Implementierng der Klasse Lottogeraet so abzuändern, dass die vorhandenen bzw. gezogenen Kugeln mit Hilfe von Ankreuzfeldern (implementiert mit Listen mit 49 Wahrheitswerten) verwaltet werden. Am Verhalten der Methoden soll sich dabei aber nichts ändern. (a) Entwickle eine passende Implementierung. Benutze zum Testen das Testprogramm aus Aufgabe 12. (b) Was muss man nach Veränderungen in der Implementierung an der Schnittstellenbeschreibung ändern?

  25. Teil 3 Beziehungen zwischen Objekten

  26. Würfelspiele Ziel ist es, Würfelspiele mit Hilfe von Objekten zu simulieren. Dabei steht hier das Zusammenspiel der Objekte im Vordergrund.

  27. Aufgabe 14 >>> >>> w1 = Wuerfel() >>> w2 = w1 >>> w3 = w1 >>> w1.werfen() >>> w1.getAugen() 6 >>> w2.getAugen() 6 >>> w3.getAugen() 6 >>> w2.werfen() >>> w2.getAugen() 4 >>> w1.getAugen() 4 >>> w3.getAugen() 4 >>> >>> w1 = Wuerfel() >>> w2 = Wuerfel() >>> w3 = Wuerfel() >>> w1.werfen() >>> w1.getAugen() 4 >>> w2.getAugen() 2 >>> w3.getAugen() 1 >>> w2.werfen() >>> w2.getAugen() 6 >>> w1.getAugen() 4 >>> w3.getAugen() 1 Schaue dir die beiden folgenden Python-Dialoge genau an (und führe sie selber durch). Worin unterscheiden sie sich? Kannst du das unterschiedliche Verhalten auch erklären?

  28. Ein Würfelbecher – Version 1 Würfelbecher werden benutzt, um Würfel so zu werfen, dass man keine Würfelergebnisse vorhersagen kann. Die Würfel werden hier nicht direkt geworfen, sondern man lässt sie aus dem Becher herausrollen. Dieser Vorgang soll mit geeigneten Software-Objekten simuliert werden. from random import randint class Wuerfel(object): def __init__(self): self.augen = randint(1, 6) def werfen(self): self.augen = randint(1, 6) def getAugen(self): return self.augen # Test wuerfel1 = Wuerfel() wuerfel2 = Wuerfel() wuerfel3 = Wuerfel() wuerfel1.werfen() wuerfel2.werfen() wuerfel3.werfen() print(wuerfel1.getAugen()) print(wuerfel2.getAugen()) print(wuerfel3.getAugen())

  29. Ein Würfelbecher – Version 1 … wuerfel1 = Wuerfel() wuerfel2 = Wuerfel() wuerfel3 = Wuerfel() … Bisher ist noch kein Objekt zur Simulation des Würfelbechers im Spiel. Ein solches Würfelbecher-Objekt soll jetzt hinzugefügt werden. Seine Aufgabe ist es unter anderem, die drei Würfel zu aktivieren. Um das zu ermöglichen, wird das Würfelbecher-Objekt mit Zeigern auf die Würfel-Objekte versehen.

  30. Aufgabe 15 #---------------------------------------- # Wuerfel #---------------------------------------- from random import randint class Wuerfel(object): … #---------------------------------------- # Wuerfelbecher #---------------------------------------- class Wuerfelbecher(object): def __init__(self): self.w1 = None self.w2 = None self.w3 = None def wuerfelHerausrollen(self): self.w1.werfen() self.w2.werfen() self.w3.werfen() (a) Die Anweisungen im Testprogramm sind durchnummeriert. Welche dieser Anweisungen werden benutzt, um die Objekte zu erzeugen und zu verbinden? # Test wuerfel1 = Wuerfel() # 1 wuerfel2 = Wuerfel() # 2 wuerfel3 = Wuerfel() # 3 becher = Wuerfelbecher() # 4 becher.w1 = wuerfel1 # 5 becher.w2 = wuerfel2 # 6 becher.w3 = wuerfel3 # 7 becher.wuerfelHerausrollen() # 8 print(wuerfel1.getAugen()) # 9 print(wuerfel2.getAugen()) # 10 print(wuerfel3.getAugen()) # 11 Aufgabe: Ergänze einen Würfel.

  31. Aufgabe 15 … class Wuerfelbecher(object): def __init__(self): self.w1 = None self.w2 = None self.w3 = None def setWuerfel(self, pW1, pW2, pW3): self.w1 = pW1 self.w2 = pW2 self.w3 = pW3 def getWuerfel(self): wListe = [self.w1, self.w2, self.w3] return wListe def wuerfelHerausrollen(self): … wuerfel1 = Wuerfel() wuerfel2 = Wuerfel() wuerfel3 = Wuerfel() becher = Wuerfelbecher() becher.setWuerfel(wuerfel1, wuerfel2, wuerfel3) becher.wuerfelHerausrollen() print(wuerfel1.getAugen()) print(wuerfel2.getAugen()) print(wuerfel3.getAugen()) (b) Worin unterscheidet sich die folgende Implementierung zum Würfelsystem von der Implementierung in Teilaufgabe (a)?

  32. Aufgabe 15 … class Wuerfelbecher(object): def __init__(self): self.w1 = None self.w2 = None self.w3 = None def setWuerfel(self, pW1, pW2, pW3): self.w1 = pW1 self.w2 = pW2 self.w3 = pW3 def getWuerfel(self): wListe = [self.w1, self.w2, self.w3] return wListe def wuerfelHerausrollen(self): … wuerfel1 = Wuerfel() wuerfel2 = Wuerfel() wuerfel3 = Wuerfel() becher = Wuerfelbecher() becher.setWuerfel(wuerfel1, wuerfel2, wuerfel3) becher.wuerfelHerausrollen() for wuerfel in …: print(…) (c) Die Ausgabe der Würfelergebnisse könnte man hier auch anders realisieren. Wie?

  33. Aufgabe 15 #---------------------------------------- # Wuerfel #---------------------------------------- from random import randint class Wuerfel(object): … #---------------------------------------- # Wuerfelbecher #---------------------------------------- class Wuerfelbecher(object): def __init__(self, pW1, pW2, pW3): self.w1 = pW1 self.w2 = pW2 self.w3 = pW3 def wuerfelHerausrollen(self): self.w1.werfen() self.w2.werfen() self.w3.werfen() (d) Schaue dir den Konstruktor der Klasse Wuerfelbecher genau an. Was ist hier anders gemacht? Wie funktioniert die Er-zeugung und Ver-bindung der Objekte? # Test wuerfel1 = Wuerfel() wuerfel2 = Wuerfel() wuerfel3 = Wuerfel() becher = Wuerfelbecher(wuerfel1, wuerfel2, wuerfel3) becher.wuerfelHerausrollen() print(wuerfel1.getAugen()) print(wuerfel2.getAugen()) print(wuerfel3.getAugen())

  34. Ein Würfelbecher – Version 2 Einen Würfelbecher kann man mit einer unterschiedlichen Anzahl von Würfeln benutzen. Die Klasse Wuerfelbecher soll jetzt so abgeändert werden, dass beliebig viele Wuerfel-Objekte verwaltet und aktiviert werden können.

  35. Aufgabe 16 #---------------------------------------- # Wuerfel #---------------------------------------- from random import randint class Wuerfel(object): … #---------------------------------------- # Wuerfelbecher #---------------------------------------- class Wuerfelbecher(object): def __init__(self): self.wListe = [] def wuerfelHinzufuegen(self, w): # ... def wuerfelHerausrollen(self): for w in self.wListe: # ... # Test wuerfel1 = Wuerfel() wuerfel2 = Wuerfel() wuerfel3 = Wuerfel() … becher = Wuerfelbecher() becher.wuerfelHinzufuegen(wuerfel1) becher.wuerfelHinzufuegen(wuerfel2) becher.wuerfelHinzufuegen(wuerfel3) … becher.wuerfelHerausrollen() print(wuerfel1.getAugen()) print(wuerfel2.getAugen()) print(wuerfel3.getAugen()) … (a) Ergänze die Implementierung der Klasse Wuerfelbecher so, dass das Testprogramm sinnvolle Ergebnisse liefert. (b) Erkläre, wie die Objektkonstellation hier aufgebaut und genutzt wird.

  36. Aufgabe 16 #---------------------------------------- # Wuerfel #---------------------------------------- … #---------------------------------------- # Wuerfelbecher #---------------------------------------- class Wuerfelbecher(object): def __init__(self): self.wListe = [] def wuerfelHineinlegen(self, pWListe): self.wListe = self.wListe + pWListe def wuerfelHerausrollen(self): for w in self.wListe: w.werfen() self.wListe = [] (c) Analysiere die folgende etwas andere Implementierung eines Würfelbechers. Worin unterscheidet sie sich von der oben betrachteten? Beschreibe in Worten, welche Objekte hier jeweils miteinander in Beziehung zueinander stehen.

  37. Aufgabe 16 # Test wuerfel1 = Wuerfel() wuerfel2 = Wuerfel() wuerfel3 = Wuerfel() wuerfel4 = Wuerfel() wuerfel5 = Wuerfel() alleWuerfel = [wuerfel1, wuerfel2, wuerfel3, wuerfel4, wuerfel5] becher = Wuerfelbecher() # 1 for wuerfel in alleWuerfel: print(wuerfel.getAugen()) print() becher.wuerfelHineinlegen([wuerfel1, wuerfel2, wuerfel3]) # 2 becher.wuerfelHerausrollen() # 3 for wuerfel in alleWuerfel: print(wuerfel.getAugen()) print() becher.wuerfelHineinlegen([wuerfel4, wuerfel5]) # 4 becher.wuerfelHerausrollen() # 5 for wuerfel in alleWuerfel: print(wuerfel.getAugen()) (d) Verdeutliche die an den markierten Stellen (#1, ..., #5) jeweils vorliegenden Objektkonstellationen mit Hilfe von Objektdiagrammen.

  38. Ein Würfelbecher – Version 3 Bei einem realen Würfelsystem existieren Würfel und Würfelbecher unabhängig voneinander. In der folgenden Simulation des Würfelsystems soll das jetzt etwas anders gestaltet werden.

  39. Aufgabe 17 #---------------------------------------- # Wuerfel #---------------------------------------- … #---------------------------------------- # Wuerfelbecher #---------------------------------------- class Wuerfelbecher(object): def __init__(self): self.wListe = [] def wuerfelHinzufuegen(self): w = Wuerfel() self.wListe = self.wListe + [w] def wuerfelHerausrollen(self): for w in self.wListe: w.werfen() def getAlleWuerfel(self): return self.wListe # Test becher = Wuerfelbecher() becher.wuerfelHinzufuegen() becher.wuerfelHinzufuegen() becher.wuerfelHinzufuegen() becher.wuerfelHinzufuegen() becher.wuerfelHinzufuegen() becher.wuerfelHerausrollen() for wuerfel in becher.getAlleWuerfel(): print(wuerfel.getAugen()) (a) Wie wird die Objektkonstellation hier erzeugt? Wie zeigt sich das im Quelltext? (b) Warum ist es in dieser Realisierung besonders einfach, weitere Würfel hinzuzufügen? Probiere es selbst aus.

  40. Aufgabe 18 (a) Verdeutliche die Objektkonstellation zu einer selbst gewählten Spielsituation mit einem Objektdiagramm. … class Spieler(object): def __init__(self, pName): self.name = pName self.wuerfel = None self.punkte = 0 def setWuerfel(self, pWuerfel): self.wuerfel = pWuerfel def wuerfeln(self): self.wuerfel.werfen() self.punkte = self.punkte + self.wuerfel.getAugen() def getName(self): return self.name def getPunkte(self): return self.punkte … wuerfel1 = Wuerfel() wuerfel2 = Wuerfel() spieler1 = Spieler('Zauberhand') spieler1.setWuerfel(wuerfel2) spieler2 = Spieler('Looser') spieler2.setWuerfel(wuerfel1) for i in range(5): spieler1.wuerfeln() spieler2.wuerfeln() print('Punktestand', spieler1.getName(), ':', spieler1.getPunkte()) print('Punktestand', spieler2.getName(), ':', spieler2.getPunkte()) print()

  41. Aufgabe 18 (b) In der gezeigten Implementierung des Spiels wird eine Kennt-Beziehung benutzt. Woran erkennt man das? Ändere die Implementierung so ab, dass Hat-Beziehungen anstelle der Kennt-Beziehungen benutzt werden. … class Spieler(object): def __init__(self, pName): self.name = pName self.wuerfel = None self.punkte = 0 def setWuerfel(self, pWuerfel): self.wuerfel = pWuerfel def wuerfeln(self): self.wuerfel.werfen() self.punkte = self.punkte + self.wuerfel.getAugen() def getName(self): return self.name def getPunkte(self): return self.punkte … wuerfel1 = Wuerfel() wuerfel2 = Wuerfel() spieler1 = Spieler('Zauberhand') spieler1.setWuerfel(wuerfel2) spieler2 = Spieler('Looser') spieler2.setWuerfel(wuerfel1) …

  42. Aufgabe 18 (c) Wir ändern das Spielsystem wie folgt ab. Beschreibe, was sich geändert hat. Implementiere und teste das neue Spielsystem.

  43. Aufgabe 18 (d) Ein Spielmanager soll eine feste / beliebige Anzahl Spieler verwalten und zum Spielen aktivieren. Zudem soll der Spielmanager nach den Spielrunden den Gewinner ermitteln. Entwickle zunächst ein Objektdiagramm für das erweiterte Spielsystem. Beschreibe das Spielsystem auch mit einem Klassendiagramm. Implementiere und teste das gesamte Spielsystem. (e) Ändere das Spielsystem aus (d) wie folgt ab: Der Spielmanager verwaltet und aktiviert eine beliebige Anzahl von Spielern. Nach jeder Spielrunde scheidet der Spieler aus, der die geringste Punktzahl hat. Wenn es keinen eindeutigen Verlierer gibt, scheidet kein Spieler aus. Gespielt wird solange, bis der Gewinner feststeht.

  44. Aufgabe 19 Wir betrachten das Spiel "chuck a luck". Das Spiel "chuck-a-luck" wird folgendermaßen gespielt: Der Spieler / die Spielerin zahlt zuerst einen Dollar (Cent) als Einsatz. Diesen setzt er / sie auf eine Zahl des Spielfeldes. Anschließend wirft er / sie drei Würfel. Der Spielanbieter bestimmt, wie viele Würfel mit der gesetzten Spielzahl übereinstimmen. Gibt es keine Übereinstimmungen, ist der Einsatz verloren, ansonsten zahlt der Spielanbieter den Einsatz zurück und zusätzlich für jede Übereinstimmung einen Dollar (Cent).

  45. Aufgabe 19 (a) Erstelle zunächst ein Objektdiagramm für eine Spielsituation. Ergänze dann das Klassendiagramm entsprechend. (b) Implementiere das Spiel passend zum Klassendiagramm. Teste die Implementierung anschließend mit einem Testprogramm.

  46. Teil 4 Vererbung

  47. Kartenstapel als Stapel Stapel werden im Alltag benutzt, wenn man Gegenstände nach dem LIFO-Prinzip verwalten möchte. LIFO bedeutet dabei "last in, first out" bzw. "wer zuletzt kommt, wir als erstes bearbeit". Kartenstapel sind spezielle Stapel, bei denen Karten nach dem LIFO-Prinzip verwaltet werden. Kartenstapel weisen zusätzliche Besonderheiten auf. Die Karten eines Kartenstapels möchte man auch mischen können. Zielsetzung: Wir werden die Klasse Kartenstapel im Folgenden neu konzipieren. Wir werden dabei ausnutzen, dass Kartenstapel als spezielle Stapel aufgefasst werden können.

  48. Stapel Zur Realisierung des LIFO-Prinzips benötigt man Operationen, um ein neues Element oben auf dem Stapel abzulegen und um das oberste Element vom Stapel zu entfernen.

  49. Aufgabe 20 Implementiere die Klasse Stapel und teste sie sorgfältig. Stapel() # erzeugt einen leeren Stapel aufDenStapelLegen(element: object) # legt element oben auf den Stapel oberstesElement(): object # liefert als Ergebnis das oberste Stapelelement oberstesEntfernen() # entfernt das oberste Stapelelement istLeer(): bool # liefert als Ergebnis True / False, je nachdem, # ob der Stapel leer ist oder nicht

  50. Stapel mit Abheben Die Modellierung der Klasse Stapel sieht nur einen Zugriff auf das oberste Element des Stapels vor. Für viele Anwendungen ist es günstig, wenn man einen ganzen Teilstapel abheben oder hinzufügen kann. Zur Realisierung dieser zusätzlichen Stapeloperationen sehen wir eine neue Klasse StapelMitAbheben vor, die die bisherige Klasse Stapel erweitert.

More Related