1 Abstrakte Datentypen

Ähnliche Dokumente
Schwerpunkte. Verkettete Listen. Verkettete Listen: 7. Verkettete Strukturen: Listen. Überblick und Grundprinzip. Vergleich: Arrays verkettete Listen

12. Dynamische Datenstrukturen

Stapel (Stack, Keller)

Algorithmen und Datenstrukturen (für ET/IT)

Abstrakte Datentypen.

Counting - Sort [ [ ] [ [ ] 1. SS 2008 Datenstrukturen und Algorithmen Sortieren in linearer Zeit

6. Verkettete Strukturen: Listen

Vorlesung Datenstrukturen

ALP II Dynamische Datenmengen Datenabstraktion (Teil 2)

Einführung in die Informatik: Programmierung und Software-Entwicklung, WS 11/12 1. Kapitel 11. Listen. Listen

1 Polymorphie (Vielgestaltigkeit)

! 1. Rekursive Algorithmen.! 2. Rekursive (dynamische) Datenstrukturen. II.3.2 Rekursive Datenstrukturen - 1 -

Grundlagen der Informatik. Prof. Dr. Stefan Enderle NTA Isny

Schnittstellen, Stack und Queue

11. Elementare Datenstrukturen

8 Elementare Datenstrukturen

Informatik 11 Kapitel 2 - Rekursive Datenstrukturen

Einfach verkettete Liste

13. Bäume: effektives Suchen und Sortieren

Programmieren in C. Rekursive Strukturen. Prof. Dr. Nikolaus Wulff

Institut für Informatik

II. Grundlagen der Programmierung. 9. Datenstrukturen. Daten zusammenfassen. In Java (Forts.): In Java:

Advanced Programming in C

Einstieg in die Informatik mit Java

Repetitorium Informatik (Java)

Theoretische Informatik 1 WS 2007/2008. Prof. Dr. Rainer Lütticke

Einführung in die Informatik: Programmierung und Software-Entwicklung, WS 11/12. Kapitel 8. Arrays. Arrays

1. Grundzüge der Objektorientierung 2. Methoden, Unterprogramme und Parameter 3. Datenabstraktion 4. Konstruktoren 5. Vordefinierte Klassen

Hochschule Augsburg, Fakultät für Informatik Name:... Prüfung "Programmieren 1", IN1bac, WS 10/11 Seite 1 von 6

Eine Klasse beschreibt Objekte mit gleichen Attributen und Methoden.

Programmieren 2 Übung Semesterwoche 2

Einstieg in die Informatik mit Java

Einführung in die Programmierung für Wirtschaftsinformatik

Folge 18 - Vererbung

Einführung Datentypen Verzweigung Schleifen Funktionen Dynamische Datenstrukturen. Java Crashkurs. Kim-Manuel Klein

Welche Informatik-Kenntnisse bringen Sie mit?

Organisatorisches. drei Gruppen Gruppe 1: 10:10-11:40, Gruppe 2: 11:45-13:15 Gruppe 3: 13:20-14:50

Einführung Elementare Datenstrukturen. Der Konstruktor muß den Listenkopf head erzeugen. Der Vorgänger und Nachfolger von head ist head selbst.

3. Übungsblatt zu Algorithmen I im SoSe 2017

Übung: Algorithmen und Datenstrukturen SS 2007

6 Speicherorganisation

(06 - Anwendungen von Stapeln und Schlangen)

Große Übung Praktische Informatik 1

Lineare Datenstrukturen: Felder, Vektoren, Listen Modelle: math. Folge (a i ) i=1.. mit Basistyp T oder: [T]

Verkettete Listen. Implementierung von einfach verketteten Listen. Implementierung von doppelt verketteten Listen

Institut für Programmierung und Reaktive Systeme 25. August Programmier-Labor Übungsblatt. int binarysearch(int[] a, int x),

Stand der Vorlesung. Vergleich verkettete Liste und sequentielle Liste

Reihungen. Martin Wirsing. in Zusammenarbeit mit Matthias Hölzl und Nora Koch 11/03

Objektorientierte Programmierung

Inhalte Informatik. I1 Grundprinzip des objektorientierten Modellierens I3 Modellieren von Netzwerkanwendungen

1. Typen und Literale (6 Punkte) 2. Zuweisungen (6 = Punkte)

Praxis der Programmierung

Algorithmen und Datenstrukturen (für ET/IT) Wiederholung: Ziele der Vorlesung. Wintersemester 2012/13. Dr. Tobias Lasser

Übungspaket 31 Entwicklung eines einfachen Kellerspeiches (Stacks)

Einführung in die Programmierung Vorlesungsprüfung

1. Aufgabe (6 Punkte): Java-Programmierung (Arrays)

1.2 Attribute und Methoden Aufbau einer Java-Klasse:

5.5.8 Öffentliche und private Eigenschaften

Teil IV : Abstrakte Datentypen (ADT)

Übungsblatt Programmierung und Software-Entwicklung Generizität, Interfaces, Listen, Sortieralgorithmen & JUnit

Programmieren 2 Java Überblick

Kapitel 9. Komplexität von Algorithmen und Sortieralgorithmen

Speicher und Adressraum

Vorkurs C++ Programmierung

Studentische Lösung zum Übungsblatt Nr. 7

Programmieren in Haskell. Abstrakte Datentypen

Dr. Monika Meiler. Inhalt

Kapitel 3: Datentyp Liste

Beispiellösung zu den Übungen Datenstrukturen und Algorithmen SS 2008 Blatt 5

8 Zugriffstypen ( Zeiger )

Programmierung im Grossen

Vorlesung Informatik 2 Algorithmen und Datenstrukturen

4.4.1 Implementierung vollständiger Bäume mit Feldern. Reguläre Struktur: Nachfolger des Knoten i sind die Knoten 2*i und 2*i+1.

Tutoraufgabe 1 (2 3 4 Bäume):

Einführung in die Informatik 1

Übung Datenstrukturen. Sortieren

Datenstrukturen und Abstrakte Datentypen

Kapitel 9. Komplexität von Algorithmen und Sortieralgorithmen

Tutorium 5 - Programmieren

C- Kurs 09 Dynamische Datenstrukturen

Algorithmen und Datenstrukturen

Objektorientierte Programmierung

Tutoraufgabe 1 (Sortieren): Lösung: Datenstrukturen und Algorithmen SS14 Lösung - Übung 4

Programmierung mit C Zeiger

Einfache Arrays. Annabelle Klarl. Einführung in die Informatik Programmierung und Softwareentwicklung

C# - Einführung in die Programmiersprache Arrays, Enumeration und Collections. Leibniz Universität IT Services Anja Aue

Softwaretechnik WS 16/17. Übungsblatt 01

Transkript:

1 Abstrakte Datentypen Spezifiziere nur die Operationen! Verberge Details der Datenstruktur; der Implementierung der Operationen. == Information Hiding 1

Sinn: Verhindern illegaler Zugriffe auf die Datenstruktur; Entkopplung von Teilproblemen für Implementierung, aber auch Fehlersuche und Wartung; leichter Austausch von Implementierungen ( rapid prototyping). 2

(Abstrakter) Datentyp vs. Datenstruktur Zur Realisierung eines Algorithmus können in der Regel unterschiedliche Datenstrukturen verwendet werden z.b., Felder oder Listen für Algorithmen auf Sequenzen von Elementen Daher ist es sinnvoll, die Schnittstelle einer Datenstruktur (also das, was die Datenstruktur kann) von der eigentlichen Implementierung zu trennen Datenstrukturen mit gleicher Schnittstelle können dann innerhalb eines Algorithmus problemlos ausgetauscht werden Der Algorithmus verwendet lediglich einen abstrakten Datentyp 3

(Abstrakter) Datentyp vs. Datenstruktur Definition: Ein abstrakter Datentyp (ADT) besteht aus einem Wertebereich (d.h. einer Menge von Objekten) und darauf definierten Operationen. Die Menge der Operationen bezeichnet man auch als Schnittstelle des Datentyps. Definition: Eine Datenstruktur ist eine Realisierung bzw. Implementierung eines ADT mit den Mitteln einer Programmiersprache (Variablen, Funktion, Schleifen, usw.). 4

(Abstrakter) Datentyp vs. Datenstruktur Die konkrete Realisierung des abstrakten Datentyps, also die verwendete Datenstruktur, bestimmt die Laufzeit der einzelnen Operationen, die auf dem Datentyp ausgeführt werden können. Insbesondere für die Analyse eines Algorithmus ist es also notwendig, die verwendete Datenstrukturen zu kennen 5

(Abstrakter) Datentyp vs. Datenstruktur Beispiel: der ADT Sequence Sequence repräsentiert eine Folge von Elementen eines gemeinsamen Grundtyps (z.b. Zahlen, Zeichenketten,...) Wertebereich: die Menge aller endlichen Folgen eines gegebenen Grundtyps Operationen: length() : int insert(type x, pos p) delete(pos p) get(int i) : Type concatenate(sequence seq) Es ist klar, dass Sequence mit Feldern oder Listen realisiert werden kann 6

(Abstrakter) Datentyp vs. Datenstruktur Laufzeiten der beiden Realisierungen des ADT Sequence: Feld: insert(x, p): im schlechtesten Fall (Einfügen am Beginn des Feldes) proportional zur Länge n des Feldes (Umsortierungen) get(i): konstante Laufzeit (direkte Addressierung über Elementindex) Liste: insert(x, p): konstant, da direktes Einfügen nach spezifiziertem Element get(i): im schlechtesten Fall proportional zur Länge der Sequenz, da Durchlauf der gesamten Liste 7

1.1 Beispiel 1: Keller (Stacks) Operationen: boolean isempty() : testet auf Leerheit; int pop() : liefert oberstes Element; void push(int x) : legt x oben auf dem Keller ab; String tostring() : liefert eine String-Darstellung. Weiterhin müssen wir einen leeren Keller anlegen können. 8

Friedrich Ludwig Bauer, TUM 9

Modellierung: Stack + + + + Stack () isempty() : boolean push (x: int) : void pop () : int 10

Erste Idee: Realisiere Keller mithilfe einer Liste! 1 2 3 4 l Das Attribut l zeigt auf das oberste Element. 11

Modellierung: Stack List Stack () + isempty() : boolean + push (x: int) : void + pop () : int + info : int + + list next + List (int x, List l) 12

Implementierung: public class Stack { private List list; // Konstruktor: public Stack() { list = null; } // Objekt-Methoden: public boolean isempty() { return list==null; }... 13

public int pop() { int result = list.info; list = list.next; return result; } public void push(int a) { } list = new List(a,list); public String tostring() { return List.toString(list); } } // end of class Stack 14

Die Implementierung ist sehr einfach;... nutzt gar nicht alle Features von List aus;... die Listen-Elemente sind evt. über den gesamten Speicher verstreut; == führt zu schlechtem Cache-Verhalten des Programms! 15

Zweite Idee: Realisiere den Keller mithilfe eines Felds und eines Stackpointers, der auf die oberste belegte Zelle zeigt. Läuft das Feld über, ersetzen wir es durch ein größeres 16

s.push(4); s sp a 1 2 3 17

s.push(5); s sp a 1 2 3 4 18

s sp a 1 2 3 4 19

s sp a 1 2 3 4 20

s sp a 1 2 3 4 5 21

Modellierung: Stack sp : int + Stack () + isempty() : boolean + push (x: int) : void + pop () : int a Array + length : int int 22

Implementierung: 23

public class Stack { private int sp; private int[] a; // Konstruktoren: public Stack() { sp = -1; a = new int[4]; } // Objekt-Methoden: public boolean isempty() { return (sp<0); }... 24

public int pop() { return a[sp--]; } public void push(int x) { ++sp; if (sp == a.length) { int[] b = new int[2*sp]; for(int i=0; i<sp; ++i) b[i] = a[i]; a = b; } a[sp] = x; } public tostring() {...} } // end of class Stack 25

Nachteil: Es wird zwar neuer Platz allokiert, aber nie welcher freigegeben Idee: Sinkt der Pegel wieder auf die Hälfte, geben wir diese frei... 26

s sp a 1 2 3 4 5 x x=s.pop(); 27

s sp a 1 2 3 4 x 5 s.push(6); 28

s sp a 1 2 3 4 6 x 5 x = s.pop(); 29

s sp a 1 2 3 4 x 6 s.push(7); 30

s sp a 1 2 3 4 7 x 6 x = s.pop(); 31

Im schlimmsten Fall müssen bei jeder Operation sämtliche Elemente kopiert werden 32

1.2 Beispiel 2: Schlangen (Queues) (Warte-) Schlangen verwalten ihre Elemente nach dem FIF0-Prinzip (First-In-First-Out). Operationen: boolean isempty() : testet auf Leerheit; int dequeue() : liefert erstes Element; void enqueue(int x) : reiht x in die Schlange ein; String tostring() : liefert eine String-Darstellung. Weiterhin müssen wir eine leere Schlange anlegen können 33

Modellierung: Queue + + + + Queue () isempty() : boolean enqueue(x: int) : void dequeue() : int 34

Erste Idee: Realisiere Schlange mithilfe einer Liste : 1 2 3 4 first last first zeigt auf das nächste zu entnehmende Element; last zeigt auf das Element, hinter dem eingefügt wird. 35

Modellierung: Queue first, last List Queue () + isempty() : boolean + enqueue(x: int) : void + dequeue() : int + info : int + next + List (x: int) + Objekte der Klasse Queue enthalten zwei Verweise auf Objekte der Klasse List 36

Implementierung: public class Queue { private List first, last; // Konstruktor: public Queue () { first = last = null; } // Objekt-Methoden: public boolean isempty() { return first==null; }... 37

public int dequeue () { if(first!= null) { int result = first.info; if (last == first) last = null; first = first.next; return result; } else write("error: NullPointerException"); return 0; } 38

public void enqueue (int x) { if (first == null) first = last = new List(x); else { last.next = new List(x); last = last.next; } } public String tostring() { return List.toString(first); } } // end of class Queue 39

Die Implementierung ist wieder sehr einfach... nutzt ebenfalls kaum Features von List aus;... die Listen-Elemente sind evt. über den gesamten Speicher verstreut == führt zu schlechtem Cache-Verhalten des Programms 40

Zweite Idee: Realisiere die Schlange mithilfe eines Felds und zweier Pointer, die auf das erste bzw. letzte Element der Schlange zeigen. Läuft das Feld über, ersetzen wir es durch ein größeres. 41

q last first a 1 x = q.dequeue(); x 42

q last first a q.enqueue(5); x 1 43

q last first a 5 x 1 44

q last first a q.enqueue(5); x 1 45

q last first a 5 x 1 46

Modellierung: Queue first : int last : int a Array int + Queue () + isempty () : boolean + enqueue (x: int) : void + dequeue () : int + length : int 47

Implementierung: 48

public class Queue { private int first, last; private int[] a; // Konstruktor: public Queue () { first = last = -1; a = new int[4]; } // Objekt-Methoden: public boolean isempty() { return first==-1; } public String tostring() {...}... 49

Implementierung von enqueue(): Falls die Schlange leer war, muss first und last auf 0 gesetzt werden. Andernfalls ist das Feld a genau dann voll, wenn das Element x an der Stelle first eingetragen werden sollte. In diesem Fall legen wir ein Feld doppelter Größe an. Die Elemente a[first], a[first+1],..., a[a.length-1], a[0], a[1],..., a[first-1] kopieren wir nach b[0],..., b[a.length-1]. Dann setzen wir first = 0;, last = a.length und a = b; Nun kann x an der Stelle a[last] abgelegt werden. 50

public void enqueue (int x) { if (first==-1) { first = last = 0; } else { int n = a.length; last = (last+1)%n; if (last == first) { int[] b = new int[2*n]; for (int i=0; i<n; ++i) b[i] = a[(first+i)%n]; first = 0; last = n; a = b; } } a[last] = x; } 51

Implementierung von dequeue(): Falls nach Entfernen von a[first] die Schlange leer ist, werden first und last auf -1 gesetzt. Andernfalls wird first um 1 (modulo der Länge von a) inkrementiert... 52

public int dequeue () { if(first >= 0){ int result = a[first]; if (first == last) first = last = -1; else first = (first+1) % a.length; } } return result; else return 0 53

Diskussion: In dieser Implementierung von dequeue() wird der Platz für die Schlange nie verkleinert... Fällt die Anzahl der Elemente in der Schlange unter ein Viertel der Länge des Felds a, können wir aber (wie bei Kellern) das Feld durch ein halb so großes ersetzen Achtung: Die Elemente in der Schlange müssen aber jetzt nicht mehr nur am Anfang von a liegen!!! 54

Zusammenfassung: Für die nützlichen (eher) abstrakten Datentypen Stack und Queue lieferten wir zwei Implementierungen: Technik Vorteil Nachteil List einfach nicht-lokal int[] lokal etwas komplexer Achtung: oft werden bei diesen Datentypen noch weitere Operationen zur Verfügung gestellt 55