TDDC30 Objektorienterad programmering i Java, datastrukturer och algoritmer. Föreläsning 3 Jonas Lindgren, Institutionen för Datavetenskap, LiU På denna föreläsning: Abstrakta datatyper Listor Stackar Köer 1
Abstrakta Datatyper (ADT) Abstraktion (subst.) En tankeprocess i vilken man bortser från vissa egenskaper hos en företeelse eller ett föremål och i stället uppmärksammar en eller några få egenskaper Källa: Nationalencyklopedin (förkortad form) Abstrakt datatyp En datatyp där man bortser från implementationsspecifika egenskaper och istället uppmärksammar en eller några få egenskaper. ADT implementeras med lämpliga datastrukturer och algoritmer Datastruktur - Logisk organisation av datorminne för lagring av data Algoritm En uppsättning instruktioner för att lösa en uppgift 2
Abstrakta Datatyper (ADT)(2) Flyttal: Ett oväntat exempel på en abstrakt datatyp(adt) Vi behöver ej känna till exakt hur flyttalet fungerar internt i datorn Detaljer kan variera mellan programspråk Formatet är rätt komplext, ex. Java definierar ett flyttal med formeln 1 s c b q, där s är 1 bit, c 23 bit, q 8 bit och c = 2 Allt vi behöver veta är operationerna, +, -, *, /, osv. Vi förväntar oss samma uppsättning operationer på flyttal överallt Endast flyttals-kontraktet måste följas Kod som använder flyttal blir därmed frikopplad från specifik implementation 3
Abstrakta Datatyper (ADT)(3) Scenario: Du skriver ett program som hanterar samtliga studenter registrerade på en kurs. Programmet ska spara för varje student om de klarat av kursen eller ej. Behov: En abstrakt datatyp(adt) som kan hjälpa till med ovannämda Steg 1: Planera en lämplig abstrakt datatyp Bestäm både både domän och operationer Steg 2: Implementera ADT:n som en datastruktur Välj representation för datat Skriv algoritmer för ADT:ns operationer Steg 3: Använd ADT:ns operationer för att beskriva algoritmen som löser ditt problem 4
Abstrakta Datatyper (ADT)(4) Steg 1: Välj lämplig abstrakt datatyp Både domän och operationer ADT: Ordbok (nyckel-information par) Domän: En linjärt ordnad mängd nycklar K (studenter) Information I (ja eller nej) Operationer: boolean lookup(nyckel) => information Ev. insättningsoperation? Fler detaljer än dessa inte synliga för användaren 5
Abstrakta Datatyper (ADT)(5) Steg 2: Implementera ADN:n som en datastruktur Välj representation av datat Konstruera algoritmer för operationerna Ni gör väl så här: (alt. implementera från ett interface) Steg 3: Använd ADT:ns operationer för att lösa din uppgift 6
Abstrakta Datatyper (ADT)(5) Sammanfattning: ADT:er säger vad som ska göras För att bestämma hur det ska göras Välj datastruktur Konstruera algoritmer för ADT:ns operationer Samma ADT kan implementeras med Olika datastrukturer Olika algoritmer Välj den lösning som är mest effektiv i just ditt fall 7
ADT Lista En av de mest använda abstrakta datatyperna Numrerad Går att hämta element m.h.a. index Går att använda Iteratorer för att traversera Abstraherar bort indexering (om man vill) Storleken: Antal element lagrade i listan Kan implementeras både med array eller nodlista 8
ADT Lista(2) En delmängd av standardgränssnittet för ADT Lista: void add(x) Lägg till x i slutet av listan void addfirst(x) Lägg till x i början av listan void remove(x), remove(i) Ta bort x /elementet på plats i boolean contains(x) True om det finns ett likadant element int indexof(x) Returnerar index för x x get(i) Returnerar elementet på index i 9
ArrayList En implementation av ADT:n Lista Representerar datat i någon form av fält + Kan hämta ut element med index snabbt - Långsam vid insättning i början av listan... 10
Enkellänkad Lista En implementation av ADT:n Lista Representerar datat i noder med referens till efterföljande nod Har ofta även ett huvud med lite extra information H D D D / + Kan lägga till element i (början av) listan snabbt - Långsam då den hämtar ut element av ett visst index... 11
Dubbellänkad Lista H En implementation av ADT:n Lista Representerar datat i noder med referens till efterföljande och föregående nod Har ofta även ett huvud med lite extra information, ibland dessutom en svans / D D D / + Snabbare att sortera - Kräver större minnesutrymme... 12
Cirkulärt länkad Lista En implementation av ADT:n Lista Enkellänkade noder i en ring Har ofta även ett huvud / markör för att peka ut den aktuella noden, ibland även en svans M D D D Implementerar vanligtvis även D Används ofta när en ringbuffer behövs D void add(x) Lägger till element efter den aktuella noden void remove() Tar bort noden efter den aktuella noden void advance() Flyttar markören ett steg 13
Iteratorer Harry har skrivit ett program som använder två cirkulära listor, en arraylista samt en dubbellänkad lista. Han vill ha ett gemensamt sätt att besöka alla värden i alla dessa datastrukturer Lösning: Iteratorer! 14
Iteratorer(2) Skapas oftast av datastrukturen Ett generellt sätt att iterera över alla element i en datastruktur Iterator i = mylist.iterator(); // Kan byta ut mylist mot alla objekt som kan // skapa en iterator while (i.hasnext()) { } System.out.print(i.next()); // Inbyggt snabbsätt att iterera över datastrukturer // Fungerar eftersom mylist har metoden iterator() for (String data : mylist) { } System.out.print(data); 15
Stack Sist in först ut (LIFO) Metoder x top() / peek() Returnerar stackens toppelement utan att ta bort det x pop() Tar bort och returnerar stackens toppelement void push(x) Lägger x på toppen av stacken boolean isempty() Returnerar sant om stacken är tom int size() Returnerar antal element i stacken Exempel på användning: Rekursion! 16
Hitta felet! public class StackTest { public static void main(string[] args) { Stack stack = new Stack(); stack.push(34); } } int i = stack.pop(); stack.push(i); stack.pop(); stack.peek(); stack.pop(); Försäkra dig om att stacken inte är tom innan du hämtar ifrån den. (Ett Exception kommer att 17 kastas här!)
Kö (en. Queue) Först in först ut (FIFO) Metoder x front() / peek() Returnerar främsta elementet x dequeue() Tar bort och returnerar det främsta elementet void enqueue(x) Lägger till x i slutet av kön boolean isempty() Returnerar sant om kön är tom int size() Returnerar antalet element i kön Exempel på användning: Inmatningsbuffert 18