• Keine Ergebnisse gefunden

Umwandlung in einen dynamischen Algorithmus

N/A
N/A
Protected

Academic year: 2022

Aktie "Umwandlung in einen dynamischen Algorithmus"

Copied!
23
0
0

Wird geladen.... (Jetzt Volltext ansehen)

Volltext

(1)

Algorithmen und Datenstrukturen 08

Stefan Ploner

15. Dezember 2011

(2)

1 Besprechung Blatt 7 Polymorphie Fragen

2 Dynamische Programmierung Allgemein

3 Fortgeschrittene Programmiertechniken Generics und komplexe Datenstrukturen 4 Vorbereitung Blatt 8

Anmerkungen

(3)

Polymorphie

Vehicle v = new Boat();

// statischer Typ: Vehicle // dynamischer Typ: Boat

v.move(); // was passiert hier?

Java geht wie folgt vor...

1 existiertmove()in Vehicle? Nein → Fehler

2 ist move()alsstaticdefiniert? Ja → Vehicle.move()

3 existiertmove()in Boat? Nein → Vehicle.move()

4 sonst → Boat.move()

(4)

Fragen zu Blatt 7?

(5)

Allgemein

hat nichts mit Dynamik zu tun

Tausch: Speicher gegen Performance

bei der ersten Berechnung werden die Ergebnisse gespeichert

bei folgenden Funktionsaufrufen wird lediglich das gespeicherte Ergebnis zur¨uckgegeben

bei nicht linearen Algorithmen ist schon im ersten Durchlauf ein Performancegewinn m¨oglich

(6)

Umwandlung in einen dynamischen Algorithmus

Speicherstruktur anlegen (Initialisieren der Klasse / 1. Aufruf)

Pr¨ufen, ob Wert vorhanden ist (vor der Berechnung)

Speichern des Ergebnisses (nach der Berechnung, immer wenn diese ausgef¨uhrt werden musste)

(7)

Details zur Speicherstruktur

als Speicherstruktur bei Funktionen mit einer Ganzzahl als Parameter eignen sich Arrays (Parameter→ Speicherzelle)

diese erm¨oglichen die ¨Uberpr¨ufung, ob der Wert bereits berechnet wurde, und gegebenenfalls die R¨uckgabe in O(1)

MAX N ¨uberlegen, sonst br¨auchte man bei einem Integer Parameter ¨uber 4 Millionen Arrayelemente

dieser Wertebereich muss dann nat¨urlich ¨uberpr¨uft werden

Funktionen mit mehreren Argumenten ben¨otigen entsprechend viele Arraydimensionen (int[MAX_N][MAX_M]...)

werden alle Werte des Array-Typs ben¨otigt, muss man sich anderswo merken, welche Felder initialisiert sind.

(8)

Fibbonacci Zahlen dynamisch

class Fibonacci {

final int MAX_N = 200;

int[] hirn;

public Fibonacci() {

hirn = new int[MAX_N + 1]; // last index: MAX_N Arrays.fill(hirn, -1);

hirn[0] = 0; // "implicit" base cases hirn[1] = 1;

}

public dynamic(int n) { if (n > MAX_N) return -1;

if (hirn[n] == -1) {

hirn[n] = dynamic(n - 1) + dynamic(n - 2);

}

return hirn[n];

} }

(9)

Schema eines dynamischen Algorithmus

(Im Konstruktor Speicherstruktur anlegen und evtl. initialisieren)

In der Berechnungsmethode

1 Parameter im Wertebereich? Nein →return;

2 Wert bereits gespeichert? Nein→ ausrechnen

3 gespeicherten Wert zur¨uckgeben

(10)

Fibbonacci Zahlen durchreichen

public static int durchreichen(int n) { if (n <= 1) return n;

return durchreichen(2, 1, 0, n);

}

// (viel Stackspeicher, besser auch entrekursivieren) public static int durchreichen(int n, int prevRes,

int prevPrevRes, int max_n) { // fib(n) = fib(n - 1) + fib(n - 2) int curRes = prevRes + prevPrevRes;

if (n == max_n) return curRes;

else {

// prevRes = curRes, prevPrevRes = prevRes return durchreichen(n + 1, curRes, prevRes, max_n);

} }

(11)

Listenklassen in der Java API

Problemstellung: Man m¨ochte einer Speicherstruktur dynamisch Daten hinzuf¨ugen und entfernen.

Bisher:Manuelles Erstellen und Kopieren von Arrays Besser:M¨oglichkeiten der Java API nutzen

List v = new ArrayList();

v.add("foo"); // add "foo"

v.add("bar"); // add "bar"

v.set(5, "bla"); // IndexOutOfBoundsException System.out.println(v.get(0)); // print "foo"

v.remove(0); // remove "foo"

(12)

Generische Listenklassen

Probleme einerArrayList:

List v = new ArrayList();

v.add("foo");

Integer i = (Integer)v.get(0); // runtime error Der selbe Code mit Generics:

List<String> v = new ArrayList<String>();

v.add("bar");

Integer i = v.get(0); // compiler error Generics dienen der ¨Ubersichtlichkeit, Fehlersuche und Performance. Die Java API bietet komplett implementierte generische Datenstrukturen f¨ur viele Anwendungsf¨alle bereit!

(13)

Wrapper-Klassen

Generic Type Parameter erlauben nur Object und dessen Unterklassen als Argument

ValueTypes erbennicht von Object(boolean, char, int, ...)

stattdessen m¨ussen sogenannte “Wrapper-Klassen” verwendet werden(Boolean, Char, Integer, ...)

dabei wird der ValueType in die Klasse eingepackt (“Boxing”) class Integer {

int value;

// probably useful Methods }

(14)

Boxing und Unboxing

Vorsicht: Obwohl es sich um Klassen handelt, weisen Wrapper-Klassen keine typische Referenzsemantik auf Ausf¨uhrliches Rechenbeispiel:

Integer a = new Integer(5), b;

b = a;

a += 5; // a = a + 5;

// a is now 10, b is still 5 Zeile 3:

1 a wird implizit nach int konvertiert (unboxing)

2 die Rechnung 5 + 5 wird ausgef¨uhrt

3 10 wird implizit nach Integer konvertiert, dabei wird eine neue Instanz erstellt (boxing)

(15)

Beispiel: Großeinkauf

Stellen Sie sich vor es ist Montag und Sie haben diese Woche besonders viele AuD-Hausaufgaben auf. Um unn¨otige Ablenkungen auf ein Minimum zu beschr¨anken, m¨ochten Sie alle

Lebensmitteleink¨aufe schon jetzt erledigen, damit Sie das Haus f¨ur den Rest der Woche nichtmehr verlassen m¨ussen.

Um dieses Ziel zu erreichen beschließen Sie, all Ihr herumliegendes Geld in Nahrungsmittel zu investieren. Um Ihre Einkaufstour zu optimieren entwickeln Sie vor dem Aufbruch einen Algorithmus, der die Eink¨aufe so ausw¨ahlt, dass so wenig ungenutztes Restgeld wie m¨oglich ¨ubrigbleibt.

(16)

Beispiel: Großeinkauf

Rekursionsidee, um diese Einkaufsliste zu erstellen:

besteListe : Einkaufsliste;

fuer jeden bezahlbaren Artikel des Supermarkts { neueListe = Rekursion mit dem restlichen Geld;

neueListe += aktuellerArtikel;

wenn neueListe teurer als besteListe { besteListe = neueListe;

} }

(17)

Beispiel: The Berch

Stellen Sie sich vor, es ist Bergkirchweih in Erlangen, und Sie gehen hin, um Ihr ganzes BAf¨oG f¨ur Juni auf den Kopf zu hauen.

Als fleißiger AuD-Teilnehmer betrachten Sie nat¨urlich auch diese Aufgabe als spannendes algorithmisches Problem f¨ur geschickte Datenstrukturen. Noch vor der ersten

”Mass Bier“ stellen Sie sich ein Array aller k¨auflichen Berg-Dinge (vom Typ

BerchWareInterface) zusammen, f¨ur die Sie grunds¨atzlich bereit sind, Ihr Geld auszugeben. Die Festwirte garantieren Ihnen, dass Sie von jedem Nahrungsmittel und jeder Dienstleistung beliebig viel haben d¨urfen, solange Sie daf¨ur noch bezahlen k¨onnen.

(18)

Erg¨anzen Sie nun die Methode Berch.getAll so, dass diese alle denkbaren Einkaufslisten zusammenstellt, die Sie mit dem Geldbetrag money (in Cent, genau wie pricePerUnit) aus dem Angebot choice gerade noch kaufen k¨onnen. Dabei ist es

entscheidend, dass Sie – wie es sich f¨ur einen typischen Studenten geh¨ort – so viel wie m¨oglich von Ihrem Geld ausgeben, d.h. jede einzelne Einkaufsliste k¨onnte nicht mal mehr mit der billigsten BerchWare erg¨anzt werden, ohne dabei

”ins Minus“ zu rutschen.

// money: maximal verfuegbares Geld // choice: alle verfuegbaren Berg-Dinge

public static BerchPurchase[][] getAll(int money, BerchWareInterface[] choice) {

(19)

Rekursionsidee, um alle bezahlbaren Listenkombinationen zu erstellen:

kaufe das erste bezahlbare Objekt in choice

berechne rekursiv alle M¨oglichkeiten, das Restgeld f¨ur die vollst¨andige Auswahl zu verprassen und f¨uge den Kauf zu jeder rekursiv ermittelten Kombination hinzu

tu so, als wolltest du das erste Objekt nie kaufen, berechne rekursiv alle M¨oglichkeiten, money ohne das erste bezahlbare Element zu verprassen

W¨ahle anschließend alle Einkaufslisten mit Restgeld<billigster choice aus

Der letzte Schritt kann weggelassen werden, wenn die Choice Liste absteigend sortiert wird. Dann werden automatisch nur maximale Einkaufslisten ausgew¨ahlt, da immer mit der letzten und billigsten

(20)

Fahrradladen

Unterteilt euren Code bitte halbwegs sinnvoll, legt Hilfsmethoden an (private!) und verseht ihn mit kurzen, pr¨azisen Kommentaren!

(21)

Heap- und Stacksize

-Xmx: maximale Heapgr¨oße

-Xss: maximale Stackgr¨oße

als Argumente beim Programmstart mit ¨ubergeben (vor dem Programmnamen!)

Beispiel: java -Xmx512m -Xss256m Fibonacci

(Das m am Ende steht f¨ur Megabyte, kein Leerzeichen dazw.)

in Eclipse unter “Run Configuration” →“Arguments” →

“VM arguments” eintragen

Bei der AufgabeZufallszahlengenerator ist es fast garantiert notwendig, den Stack zu vergr¨oßern!

(22)

Zufallszahlengenerator

In der Aufgabe geht es um Endrekursivierung, nicht um Entrekursivierung!

(23)

0-Punkte-Generator

Erinnerung an Blatt 0: “Schnittstellen¨anderung”

“Die Schnittstellen von Methoden und Klassen d¨urfen nicht ver¨andert werden.”

“Auch f¨ur Klassen!”

D.h., dass s¨amtliche selbst hinzugef¨ugten Attribute und Methoden mit der Sichtbarkeit privateversehen werden m¨ussen, ansonsten gilt auch hier die 0 Punkte Regelung!

Das impliziert, dass beim Zugriff auf andere Klassen nur die gegebenen Schnittstellen verwendet werden d¨urfen. (Z.B. kein direkter Zugriff auf (ohnehin verbotene) eigene

public-Attribute)

Referenzen

ÄHNLICHE DOKUMENTE

[...] und ein niedliches Haustier darfst du bestimmt schon lange haben (Brief 8). Im Fall von Mario zeigte sich eine Identifikation jedoch am stärksten, indem er die

Gegenanzeigen: Keine Anwendung bei Magengeschwüren, Überempfi ndlichkeit gegen die Wirkstoffe, gegen andere Apiaceen (Umbelliferen, z. Anis, Fenchel), gegen Anethol (Bestandteil

Sämtliche Punkte ( liegen daher auch bei der geschränkten Schub- kurbel auf einem Kreise um M als Mittelpunkt mit einem Halbmesser gleich der Länge der Exzenterstange, nur ist

Häufiger ist die andere Art, die aber hier zunächst nur in einer allgemeineren, wenn auch selten angewendeten Gestalt ‚untersucht werdensoll. III, werde durch die geschränkte

Gewöhnlich begnügt man sich aber in dieser’ Rich- tung mit einer Annäherung und führt entweder den Mittelpunkt oder einen der Endpunkte der Koppel in einem durch M’M”, V’V”

Der unterste Punkt der Koppel wird vomKreuz- kopfe durch eine kurze Zugstange mitgenommen, der andere von einem senkrecht zur Kurbel stehenden Exzenter, dessen Stange nach

Wird nun die Steuerwelle zunächst so eingestellt, dass sich der Stein in der Horizontalen OS bewegt, so liegt eine einfache Schub- kurbel mit einem Voreilwinkel von 90° vor, und

Sie kommen darauf hinaus, anzunehmen, der Endpunkt D der Exzenter- stange bewege sich bei jeder Einstellung in einer zur Schubrichtung des Schiebers parallelen, horizontalen