Pensum. Grunnleggende. Sorting and order statistics

Størrelse: px
Begynne med side:

Download "Pensum. Grunnleggende. Sorting and order statistics"

Transkript

1 Side 1 for TDT4120 algdat Pensum 25. august : Introduction 2 - Insertion sort Analysering designe algoritmer 3 Asymptotisk notering Funksjonsvekst standard notering vanlige funksjoner Monotonicity Tak og gulv Modulær aritmetikk Polynomer Eksponentialer Logaritmer Fakultet Funksjonell iterasjon Iterated logaritme funksjon (??) Fibonacci Divide and conquer Rekurrens Substitusjonsmetode for å løse rekurrenser Trerekursjon for å løse rekurrenser Masterteorem for å løse rekurrenser Grunnleggende Heaps Heapsort algoritme Maintaining heap property Building heap prioritetskøer Quicksort Performance of quicksort A randomized version of quicksort Sortere i lineær tid Lavere grenser for sortering Decision-tree model Counting Sort Radix sort Bucket sort 9: Medians and order statistics Minimum og maksimum Selection in expected linear time Selection in worst-case linear time Sorting and order statistics

2 Side 2 for TDT4120 algdat 10.1,2,4 - Elementære datastrukturer Stacks og køer Linked lists Representere rotfestede trær Hash-tabeller Direct-address tables Hash tables Hash functions, køddent Open addressing Binære søketrær Hva? Querying a binary search tree Insertion and deletion Datastructures Nesten ferdig, litt forståelse av hashing 15 Dynamisk programmering Rod cutting Matrix-chain multiplication Elements of dynamic programming Longest common subsequence Optimal binary search trees Grådige algoritmer An activity-selection problem Elements of the greedy strategy Huffman codes Har ikke helt skjønt hvordan dette skal bevises Advanced design and Analysis techniques Representations of graphs Breadth-first search, ikke lest helt ferdig Depth-first search, LEST FERDIG Topological sort Sterkt koblede komponenter 23 Minimum spanning trees Growing a minimum spanning tree The algorithms of Kruskal and Prim Kjøretid!! Graph algorithms Single-source shortest paths The bellman-ford algorithm Single-source shortest paths in directed acyclic graphs Dijkstra's algoritme The Floyd-Warshall algorithm All pairs Floyd warshall Maximum flow Flow networks The Ford-Fulkerson method Maximum bipartite matching NP-complete problems Selected topics

3 Side 3 for TDT4120 algdat Motivasjonsboost: OVER HALVVEIS!! Lest 11 kapitler!! 8 igjen!!! 7 IGJEN!! SNART TRE FUCKINGS KAPITLER IGJENNNN

4 Side 4 for TDT4120 algdat Cormen: 1 5. august : Algoritmer Algoritme Probleminstans Korrekt algoritme Forskjellige eksempler Datastruktur Effektivitet NP-komplette problemer Veldefinert computational prosedyre som tar en mengde inputverdier, og gir en mengde output-verdier. Et verktøy for å løse computational problems. Et spesifikt input En korrekt algoritme gir riktig output for alle instanser. Finne korteste vei mellom to kanter i en graf Dynamisk programmering - finne lengste felles delmengde til to forskjellige ordnede mengder. Lineær programmering - Finne mest effektive et eller annet. Numeriske algoritmer og tallteori - Sikkerhet og kryptografi Søking og databaser Noe med "Convex hull" En måte å lagre og organisere data, for tilgang og modifikasjoner. Måles i fart - jo fortere, jo mer effektiv. Problemer der man ikke har funnet en mest effektiv løsning. Ikke bevist at en effektiv løsning ikke finnes, og hvis man finner en effektiv løsning til ett problem, finnes en for alle. Parallellitet Prosessorer består av flere kjerner, for effektivitet -> Finne algoritmer som jobber parallelt. Oppgaver Eksempel på sortering: En database med navn ordnet alfabetisk, der man kan legge til/fjerne navn. Hvis databasen i utgangspunktet er sortert, kan man lettere legge inn navn på riktig plass. Andre måter å måle effektivitet: Hvis man skal lage en digital maskin, kan man måle effektivitet etter hvor mange transistorer som trengs. Eksempel på datastruktur: Linked list i java. Der er elementene i listen lagret som noder i en graf, etter hverandre. Hvis man skal fjerne eller legge til elementer på en plass i listen, kan man bare endre naboskapet mellom nodene. Hvis man derimot er ute etter å nå elementene på spesifikke plasser, må man iterere gjennom alle elementene, til man kommer til riktig plass. Korteste sti og reisende selger: 1.2 Algoritmer som teknologi Flettesortering og innsettingsortering Merge sort er best, pga O(n logn) < O(n 2 )

5 Side 5 for TDT4120 algdat (merge og insertion) Viktighet Alt vil ta nytte av algoritmer, så algoritmer er viktig, basically.

6 Side 6 for TDT4120 algdat Cormen: 2 7. august : Algoritmer som teknologi Insertion sort Effektivt for få elementer. 1) Begynner på element nr. 2 i en liste 2) Sjekker om element nr. 2 er mindre enn nr. 1 3) Fortsetter videre, ved å sammenligne element nr. n, og sammenligner med n-1, n-2,,1 4) På den måten er alle elementer fram til element nr. n sortert. Loop invariant En betingelse - brukes som hjelp for å forstå hvorfor en algoritme er korrekt. Man setter en betingelse for dette, tester algoritmen i tre steg: Initialisering Betingelsen er sann før første iterasjon. Maintenance Hvis den er sann før iterasjonen, er den fortsatt sann før neste iterasjon. Terminasjon Når løkken avsluttes, gir invarianten et brukbart resultat som hjelper til å vise at algoritmen er korrekt. [Fra itgk]: Initialisering - Etablerer en initiell tilstand som modifiseres mot termineringsbetingelsen. Test - sammenligner nåværende tilstand med termineringsbetingelsen, og terminerer hvis den er lik. Endre - Endrer tilstanden på en slik måte at den nærmer seg termineringsbetingelsen. Eksempel på loop invariant: På starten av hver iterasjon i løkka, består lista A[1,..,j-1] av de samme, første j-1 elementene i den originale lista, bare sortert. 2.2 Analysere algoritmer Analysere algoritmer Hva skal måles etter? Input-størrelse Kjøretid Eks. med Hvor mye ressurser trenger en algoritme? Trenger en modell for en implementasjonsteknologi, for eksempel RAM. Generelt vokser tiden til en algoritme med størrelsen på inputtet, så det er vanlig å beskrive tiden som en funksjon av inputtet. Avhenger av problemet Antall primitive operasjoner, eller steg. I boka: Definert som hver linje i koden.

7 Side 7 for TDT4120 algdat insertion sort Beste fall: Alle elementer i listen er sortert. Når vi kommer til while-løkka, blir det én sjekk per for-runde. Slik at: Denne reduseres til an + b, en lineær formel. Verste fall: Alle elementer i listen er sortert i motsatt rekkefølge. Da blir tj = j, og det viser seg at utrykket man får kan reduseres til et andregrads uttrykk. Hvorfor se på verstefalls scenario? Gir en øvre grense I noen algoritmer skjer verstefalls scenario ganske ofte - for eksempel i søking. Gjennomsnitts scenario er ofte vel så dårlig som verstefall. Order of growth Bruker bare n av høyeste orden (storeo). 2.3 Designe algoritmer Designe algoritmer Splitt og hersk Flettesortering Merge sort Innsettingssortering - inkrementell fremgangsmåte. Deler et problem opp i mindre deler/problemer. Løser problemet rekursivt. Splitt problemet opp i et antall delproblem, som er mindre instanser av samme problem. (Divide) "Hersk over" delproblemene ved å løse dem rekursivt. Hvis de er små nok, løs de rett frem. (Conquer) Kombiner løsningene til delproblemene inn i det originale problemet (Combine) Splitt og hersk teknikk. Del opp n-listen i to n/2-lister. (Divide) Sorter dellistene rekursivt, med flettesortering. (Conquer) Flett sammen de to sorterte dellistene, for å få det sorterte svaret. (Combine)

8 Side 8 for TDT4120 algdat Testing Loop invariant Rekursiv ligning, eller rekurson Analysering av algoritme HUSK, første indeks 1!!! Betingelse: På starten av hver iterasjon av for-løkka i linja 12-17, består dellisten A[p..k-1] av de k-p minste elementene av L[1..n1+1] og R[1..n2+1] i sortert order. I tillegg er L[i] og R[j] de minste elementene i hhv. R og L, som ennå ikke er kopiert tilbake i A. Initialisering: Før første initialisering er k = p, så A[p..k-1] er tom. Denne tomme dellisten består de k-p = 0 minste elementene av R og L, og siden i = j = 1, er L[i] og R[i] de minste elementene i sine lister, som ikke ennå er kopiert i A. Test: Antar først: L[i] <= R[j]. Da er L[i] minste element som ikke er kopiert inn i A. Siden A[p.. k - 1] består av de k-p minste elementene, etter linje 14 blir L[i] kopiert inn i A[k], der dellisten A[p.. K] består av k-p+1 minste elementene. Inkrementering av k og i, i linje 15, restabiliserer testbetingelsen. Hvis L[i] > R[j], skjer passende handling. Terminasjon: Ved terminasjon, k = r+1, består dellisten a[p.. k-1] = a[p..r] av de k-p = r-p+1 minste elementene av L og R, i sortert rekkefølge. Listene L og R består begge av n1+n2+2 = r-p+3 elementer. Alle elementer er blitt kopiert tilbake i A, bortsett fra de to største elementene, som er satt til uendelig. En algoritme som består av et rekursivt kall til seg selv. Splitt: Tar konstant tid, D(n) = Theta(1) Hersk: Løser rekursivt to delproblem, hver med størrelse n/2, som legger til 2T(n/2) til tid. Kombiner: Flette-prosedyre på en liste med n elementer tar Theta(n) tid, så C(n) = Theta(n) Master theorem (kap 4) viser at T(n) = n*lg2(n) Dette kan også vises ved å se på et 2-tre. Se side 37/38 (59, pdf)

9 Side 9 for TDT4120 algdat Cormen: september : Asymptotisk notasjon Theta-notasjon Definisjon: For en gitt funksjon g(n), beskriver Theta(g(n)) mengden med funksjoner: Θ ( ) = { ( ):, 0 ( ) ( ) ( ) } Det må altså eksistere konstanter c1 og c2 slik at f(n) blir "sandwhiched" mellom c1*g(n) og c2*g(n). Vi bør bruke mengdenotasjon (a \in A), men skriver i stedet ofte: f(n) = Theta(g(n)) Hvordan vise at f(n) = Theta(g(n))? Vi sier at g(n) er en asymptotisk tett grense for f(n). O-notasjon Sett opp uttrykket som over. Del på asymptotisk (riktig bruk?) største variabel. Finn så passende c1 og c2 som gjelder for n >= n0 Definisjon: For en gitt funksjon g(n) beskriver O(g(n)) mengden funksjoner: ( ) = { ( ): 0 ( ) ( ) } Omeganotasjon Gir en øvre grense for en funksjon Merk at f(n) = Theta(g(n)) impliserer O(g(n)) Definisjon: For en gitt funksjon g(n) beskriver Omega(g(n)) mengden funksjoner: Ω ( ) = { ( ): 0 ( ) ( ) } Gir en nedre grense for en funksjon Uansett hva n er, vil kjøretiden minst være en konstant ganger Omega(g(n)) Gir en nedre grense for beste tilfelle.

10 Side 10 for TDT4120 algdat Grafisk eksempel av Theta-, Omegaog O-notasjon Teorem 3.1 Bruke asymptotisk notasjon i likninger. o-notasjon (liten o). omega-notasjon (liten omega) Sammenligne funksjoner For enhver to funksjoner f(n) og g(n) har vi at f(n) = Theta(g(n)) hvis og bare hvis f(n) = O(g(n)) og f(n) = Omega(g(n)). Når vi skriver: f(n) = Theta(g(n)) mener vi at f(n) er i mengden Theta(g(n)). Men dette gjelder ikke når vi skriver: f(n) = an^2 + bn + c = an^2 + Theta(n) Da bruker vi Theta-notasjon i en likning, og i dette tilfellet betyr Theta(n) en eller annen funksjon i mengden Theta(n). Dette brukes ofte fordi noen ledd rett og slett ikke er så veldig viktige. Når vi bruker store O-notasjon, kan grensen være asymptotisk tett eller ikke. 2n^2 = O(n^2) er asymptotisk tett, og 2n = O(n^2) er ikke asymptotisk tett. Når vi bruker lille o-notasjon, beskriver vi en øvre grense som ikke er asymptotisk tett. 0 <= f(n) <= c(g(n)) gjelder for alle konstanter c, når f(n) = o(g(n)). ( ) lim = 0 ( ) omega-notasjon er til Omega-notasjon som o-notasjon er til O- notasjon. Beskriver en asymptotisk nedre grense som ikke er tett. Grenseverdien til f(n)/g(n) når n går mot uendelig er uendelig.

11 Side 11 for TDT4120 algdat Analogi til reelle tall Trikotomi holder IKKE 3.2 Standard notasjon og vanlige funksjoner Monoton Takfunksjon Gulvfunksjon En funksjon f(n) er - monotont stigende hvis m <= n impliserer f(m) <= n - monotont synkende hvis m <= n impliserer f(m) >= f(n) - Strengt økende hvis m < n impliserer f(m) < f(n) - Strengt avtagende hvis m < n impliserer f(m) > f(n) Runder opp Runder ned Mer om gulv- og takfunksjon på s. 54 (75)

12 Side 12 for TDT4120 algdat Cormen: september : Substutisjonsmetoden for å løse rekurrenser Substutisjonsmetoden Eksempel 1) Gjett formen på løsningen 2) Bruk matematisk induksjon til å finne konstantene, og vise at løsningen fungerer. Vi har en rekurrens, og skal finne øvre grense: Vi gjetter at en løsning er T(n) = O(n log n). Da må vi vise at T(n) <= cn log n, der c er en konstant større enn null. Vi antar at dette gjelder for alle m < n, spesielt m = floor(n/2), som gir ( ) 2 lg 2. Og ved å sette dette inn i rekurrensen, blir det: Base case Gjetting Subleties Side 85 (106) Unngå pitfalls Endre variabler Der siste steget holder, så lenge c >= 1. Noen ganger kan det være vanskelig å bevise rekursjonens base case med induksjon. I tilfellet over, kan base case være n = 1, men da blir O(n lg n) = 1 lg 1 = 0. Og dette er feil. Man velger derfor en egen base case for at induksjonen skal holde, og beviser for n >= n0, der n0 velges fritt. Hvis en rekurrens er lik en man har sett før, kan man gjette med en lignende løsning. Bevis løse øvre og nedre grenser, og deretter reduser usikkerheten. Når vi skal bevise at T(n) = O(n), må vi eksplisitt bevise at T(n) <= cn for en konstant c. Hvis man har en ligning som ligner på en du har sett tidligere, kan man ved å endre variabler få den til å slik. Se eksempel på sida. 4.4 Rekursjonstre metoden for å løse rekurrenser Metoden Hvis man har en rekursjon, kan et rekursjonstre bruker for å regne ut asymptotisk kjøretid. Man lager et tre som tilsvarer kall til delproblem, der hver node representer tiden til hvert delproblem, og deretter summeres alle problem for hvert nivå, og så summeres alle nivå. Dette kan kombineres med substitusjon, slik at man ved hjelp av et rekursjonstre kan gjette en løsning, og deretter bruke substutisjon. Da kan man være "sloppy" når man lager treet. Man kan også være nøye når man lager treet, og direkte bevise det.

13 Side 13 for TDT4120 algdat Les mer Se eksempel med tre på side 90 (111) 4.5 Masterteorem Masterteorem Denne er viktig I tilfelle 1 eller 3 er det viktig at f(n) er polynomisk mindre enn, eller større enn O(n logb (a +/- c) ). Det er flere eksempler på bruk av masterteoremet på side 95 (116)

14 Side 14 for TDT4120 algdat Cormen: september : Hauger (heaps) Binære hauger Binære hauger er et liste-objekt som kan sees på som en nesten komplett binært tre (fylt opp på alle nivå, bortsett fra kanskje det siste nivået, der det er fullt fra venstre). Listen har to atributter: - Lengde, som gir antall elementer i lista. - Haug-størrelse som representerer hvor mange elementer av haugen som er lagret i lista, der 0 <= haug-størrelse <= lengde. NOTIS Finne forelder, element til høyre og element til venstre. Begynner ofte å telle på 1 i heap - altså at første element i ei liste har plassering 1. Dette må modifiseres når man faktisk implementerer lista. Maks-haug Min-haug Haugsortering Høyde Der i er indeksen til lista (tallet over i treet). A[Parent(i)] >= A[i] Altså, verdien til en node er større enn eller lik verdien til barna til noden. Motsatt fra maks-haug: A[Parent(i)] <= A[i] Verdien til en node er mindre enn, eller lik verdien til barna. Bruker maks-haug. Mer om seinere. - Høyden til en node er definert som en enkel sti nedover til et blad. - Høyden til en haug er høyden til roten, og er Theta(lg n) 6.2 Opprettholde heap-egenskaper Max-Heapify

15 Side 15 for TDT4120 algdat Litt forskjellig ordvalg fra plass til plass på hva som er max-heapify. I tillegg til pseudokoden ovenfor, kjøres [pseudokoden] på alle noder fra n//2 og nedover (fra siste node i lista sin forelder). Dette kalles ofte max-heapify, og da kan denne lille kodesnutten typisk kalles "sift down" elns. Se foiler for mer pseudokode. Max-Heapify kjøres på node i, og antar at barna til i opprettholder max heap-egenskapen. Hvis de ikke gjør det, gjøres endringer slik at de gjør det. Da må max-heapify kjøres på den noden som i ble plassert på, for å forsikre om at den opprettholder max-heapegenskapen. Kjøretid Tiden det tar å kjøre max-heapify på et deltre med størrelse n, rotfested på en node i, er tiden det tar å fikse forholdet mellom i og barna, Theta(1), pluss tiden det tar å kjøre max-heapify på et deltre rotfestet på et av barna til i. Det er maks 2n/3 noder i deltrærne, så kjøretiden kan beskrives med: T(n) <= T(2n/3) + Theta(1) Ved bruk av masterteoremet, finner vi at dette tar O(lg n) tid. 6.3 Bygge en heap Build-Max-Heap Også kalt max-heapify. Forklarer den over. Bevis: Betingelse: På starten av hver for-løkke er node i + 1, i + 2,, i + n roten til en max-heap. Initialisering: På starten av første for løkke, i = n//2, så er alle noder n//2 < i <= n løv, og opprettholder derfor maxheap-egenskapen. Maintenance: Se at alle barn til node i er nummerert høyere

16 Side 16 for TDT4120 algdat enn i. På grunn av løkke-betingelsen er det begge røtter til max-heaper. Dette er betingelsen for å kunne kjøre maxheapify. Max-heapify sørger også for at alle røtter til i er max-heaper. Kjøretid Terminasjon: Ved terminasjon, i = 0, er alle noder roten til en max-heap. Ved første øyekast, så tar build-heap O(n lg n) tid, for vi kjører gjennom n noder, og kjøring av max-heapify på hver node tar O(lg n) tid. Men hvis man ser nærmere, så ser man at man begynner på node n//2, på nivå 2. Nivå 2 har n/4 noder, og hvert kall max-heapify tar O(1) tid. Neste nivå har n/8 noder, og vi kan kalle på max-heapify én gang til per node. Videre, så har neste nivå n/16 noder, og max-heapify kan kalles på to ganger til. Slik at for hvert nivå minskes antall noder, men antall potensielle rekursive kall økes. Det viser seg at dette tilsvarer en konstant, og en tettere øvre grense for build-heap er O(n) tid. 6.4 Heap-sortering Heap-sort 1) Bygger først en heap ut av listen A. 2) Itererer gjennom lista fra A.length ned til 2 [i blir størrelsen på heapen]. 3) A[1] og A[i] (str på heap) bytter plass, fordi A[1] er det største elementet i lista, og blir plassert på siste plass i

17 Side 17 for TDT4120 algdat Kjøretid Fun fact 6.5 prioritetskøer Prioritetskøer Bruke heap som prioritetskø heapen. 4) Endrer heap-size 5) Forsikrer at første element i lista opprettholder max-heapegenskapen. Heapsort tar O(n lg n) tid, siden Build-Max-Heap tar O(n) tid, og hvert av de n - 1 kallene til max-heapify tar O(lg n) tid. God implementasjon av quick sort slår heap sort. En maks-prioritetskø inneholder metodene: Insert(S, x): Setter elementet x inn i mengden S. Maximum(S): Returnerer elementet til S med størst nøkkel. Extract-Max(S): Fjerner og returnerer elementet i S med størst nøkkel. Increase-Key(S, x, k): Øker verdien til element x's nøkkel til den nye verdien k, som er forventet å være minst like stor som x's nåværende verdi. Heap-maximum(A): Tar O(1) tid, er bare å returnere A(1) Heap-Extract-Max(A): Tar O(lg n) tid. Returnerer A(1), setter siste element i A til å være A[1], reduserer A.heap_size med 1, kjører Max-Heapify på node 1 for å opprettholde max-heapify. Heap-Increase-Key(A, i, key): Setter node i's nøkkel til key, hvis key er større enn nåværende nøkkel. Traverserer deretter oppover i treet, og sammenligner node i med nodene som traverseres, i tilfellet foreldrenodene's nøkkel er mindre enn node i's nøkkel. Bytter i så fall plass med foreldrenode. Tar O(lg n) tid. Max-Heap-Insert(A, key): Øker størrelsen til heapen med 1. Setter A[A.heap_size] til minus uendelig. Kaller Heap-Increase-Key(A, A.heap-size, key). Tar O(lg n) tid).

18 Side 18 for TDT4120 algdat

19 Side 19 for TDT4120 algdat Cormen: oktober : Quicksort Beskrivelse Algoritme Bruker splitt og hersk-teknikk: Splitt: Ordne listen A[p..r] i to dellister, slik at alle elementer i A[p..q] er mindre enn A[q] og alle elementer i A[q + 1..r] er større enn A[q] Hersk: Sorter dellistene fra splitt ved å kalle på quicksort. Kombiner: Siden dellistene er sortert, trengs ingen arbeid for å kombinere dem og hele listen A[p..r] er sortert. Partisjonering av lista: 1) Setter siste element i A[p..r] til x. 2) Setter i til p-1 (elementet før første element i A[p..r]) 3) Traverserer lista fra første til nest siste element. 4) Hvis element j er mindre enn eller lik siste element: 5) I inkrementeres med 1. 6) i og j bytter plass, slik at alle tall som er mindre enn A[r] er på starten av lista og alle som er større enn A[r] er på slutten av lista. 7) A[r] og A[i + 1] bytter plass, slik at alle elementer før i + 1 er mindre enn A[i+1] og alle elementer etter i + 1 er større enn A[i + 1]. 8) Returnerer i + 1. Se bevis på side Performance of quicksort Kjøretid Verstefalls partisjonering Kjøretiden kommer an på om partisjonen er balansert eller ikke. Hvis partisjonen er balansert, kjøres algoritmen like fort som flettesortering. Hvis ikke, kan den kjøre like sakte som innsettsortering. Verstefalls scenario er om partisjoneringen gir et delproblem med n-1 elementer og et med 0 elementer. Partisjonering koster Theta(n) tid, og T(0) = Theta(1) Slik at rekurrensen for kjøretiden er:

20 Side 20 for TDT4120 algdat T(n) = T(n-1) + T(0) + Theta(n) = T(n-1) + Theta(n) Hvis vi summerer kostnadene på hvert nivå av rekursjonen, får vi en aritmetisk serie (se appendiks 2), som tilsvarer Theta(n^2). Det gir: T(n) = Theta(n^2) for verstefalls scenario Bestefalls partisjonering Verstefalls scenario skjer hvis lista allerede er sortert, noe som tar O(n) tid med innsettingssortering. Partisjonering gir to delproblem, hver med størrelse ikke større enn n/2. Delproblem 1 har floor(n/2) elementer Delproblem 2 har ceil(n/2) - 1 elementer Det gir rekurrens: T(n) = 2T(n/2) + Theta(n) Der vi tolerer å fjerne gulv- og takfunksjonene. Ved case 2 i masterteoremet gir dette løsningen Balansert partisjonering T(n) = Theta(n lg n) Kjøretiden til gjennomsnittstilfellet er mye nærmere bestefallstilfellet enn verstefallstilfellet. "The key to understanding why is to understand how the balance of the partitioning is reflected in the recurrence that describes the running time." Si at partisjonsalgoritmen alltid gir en 9-til-1 proposjonal splitting. Da får vi rekurrensen T(n) = T(9n/10) + T(n/10) + cn Merk at hvert nivå av treet koster cn, helt til rekursjonen når dybden log10(n) = Theta(lg n), og da koster nivåene ikke mer enn cn. Rekursjonen avsluttes etter log10/9(n) = Theta(lg n), slik at quicksort kjører i O(n lg n) tid - Asymptotisk det samme som i bestefallspartisjonering. Gjennomsnittstilfellets intuisjon Det viser seg at enhver konstant proposjonal splitting gir et rekursjonstre med dybde Theta(lg n), og dermed en kjøretid som er O(n lg n). Gjennomsnittstilfellet vil gjerne gi en blanding av (tilnærmet) bestefallspartisjonering og verstefallspartisjonering. Og det viser seg at hvis man har et tilfellet som gir verstefallspartisjonering og bestefallspartisjonering annenhver gang. Det viser seg at dette likevel tar O(n lg n) tid, men med en skjult konstans som er høyere enn med bare gode splittinger. 7.3 Tilfeldiggjort versjon av quicksort Hvorfor? For å hindre at samme input alltid gir samme, dårlige kjøretid.

21 Side 21 for TDT4120 algdat Hva gjør vi? I stedet for å bruke x = A[r] som pivot, velger vi heller et tilfeldig element i A[p, r] som pivot. På den måten, forventer vi at partisjoneringen er reasonably velbalansert gjennomsnittlig. Måte å implementere dette på:

22 Side 22 for TDT4120 algdat Cormen: 8 - Sortering i lineær tid 10. oktober : Lavere grenser for sortering Decision tree Eksempel Vi kan bruke bestemmelsestrær til å finne lavere grenser for en bestemt sorteringsalgoritme / sammenligningsalgoritme. Decision tree I et bestemmelsestre blir hver interne node betegnet med i:j for en i og en j, der 1 <= i < j <= n, der n er antall elementer. Bladene tilsvarer en permutasjon (antall måter å ordne ) av listen, altså resultatet av sorteringen. Se over. En nedre grense for verstefalls scenario Utføring av en sorteringsalgoritme tilsvarer å lage en enkel sti fra roten av treet ned til et løv, der hver kant tilsvarer en sammenligning mellom i og j. Når vi kommer til et blad, har sorteringsalgoritmen gitt en sortering. Siden alle korrekte sorteringsalgoritmer må kunne produsere hver permutasjon av innputtet, må alle n! permutasjoner av n elementer forekomme som løv i treet for at sammenligningen skal være korrekt. I tillegg må alle bladene kunne nåes fra roten ned fra en sti som tilsvarer en faktisk utføring av sorteringen. Verstefalls scenario av en sortering tilsvarer det meste antall sammenligninger man må gjøre, som tilsvarer den lengste stien fra roten i et bestemmelsestre og ned til en node. Det vil si høyden til treet. Teorem 8.1 Alle sammenligningsalgoritmer trenger Omega(n lg n) sammenligninger i verstefall. Bevis på side 193 (214) Korollar Heapsort og flettesortering er asymptotisk optimale sammenligningssorteringer. 8.2 Tellesortering Antagelse Det finnes k mulige forskjellige verdier.

23 Side 23 for TDT4120 algdat Tellesortering Kjøretid Stabil 1-3) Setter C til å være en liste med k elementer, der element = 0. k er det største elementet i A. 4-5) Teller hvor mange det er av hvert element, slik at C[i] sier hvor mange det er av elementet i. 7-8) Teller hvor mange elementer som er mindre enn, eller lik i, slik at C[i] er antallet elementer som er mindre enn eller lik i ) Nå vil hvert element C[A[j]] si hvilken indeks verdien A[j] skal settes inn i B på for riktig sortering. I tilfellet det er flere verdier av A[j] som er like, dekrementeres C[A[j]] med 1. Hvor mye tid tar algoritmen? 2-3: Theta(k) 4-5: Theta(n) 7-8: Theta(k) 10-12: Theta(n) Slik at algoritmen tar Theta(k + n) tid. Vi bruker som regel denne algoritmen hvis k = O(n), slik at den tar Theta(n) tid. - Hvorfor har denne en verstefalls nedre grense som er asymptotisk mindre enn Omega(n lg n)? Dette er ikke en sammenligningsalgoritme. Vi kan derfor ikke anta at den nedre grensa er Omega(n lg n). Tellesortering er stabil - det vil si at tall med samme verdi i innputtlista vil bli lagt i samme rekkefølge i utputtlista. Så tallet som kommer først i innputtlista vil også komme først i utputtlista. 8.3 Radikssortering Radikssortering Hvis hvert tall består av d siffer, kan de sorteres ved å se på minste signifikante siffer, LSD, sortere etter det, deretter flytte en radiks opp og sortere, osv, til mest signifikante siffer.

24 Side 24 for TDT4120 algdat Dette krever at sorteringen som blir brukt på hver tierplass i tallet må være stabil. Det er typisk å bruke tellesortering til dette. Lemma 8.3 Lemma 8.4 Dette kan for eksempel bli brukt hvis man sorterer datoer. Gitt n tall med d siffer, der hvert siffer kan ha verdier k forskjellige verdier, sorterer Radix-Sort disse tallene riktig med Theta(d(n + k)) tid hvis den stabile sorteringen bruker Theta(n + k) tid. Bevis side 198 (219) Gitt n tall med b siffer, og et positivt heltall r <= b, vil Radix- Sortering sortere disse tallene med Theta( (b/r)(n + 2 r ) ) tid hvis den stabile sorteringen bruker Theta(n + k) tid for innputt i intervallet 0 til k. Bevis side 199 (220) 8.4 Bøttesortering Antagelser Alle elementer i en liste med n elementer ligger i intervallet [0..1), og elementene er også tilfeldig, uniformt fordelt i intervallet. Bøttesortering 1-2: B en liste med n elementer fra 0 til n-1 og n er antall elementer i A. 3-4: Putter lister i alle plassene til B. 5-6: Vi kan se på A[i] som en "andel", så floor(a[i]*n) tilsvarer riktig indeks i B, slik at alle tall som har d som første desimaltall blir plassert på B[d]. Dvs, floor(n*a[i]) = d

25 Side 25 for TDT4120 algdat Kjøretid 7-8: Sorter listene i B med innsettsortering 9: Sett sammen listene i riktig rekkefølge. Med antagelsen om at elementene er uniformt fordelt over intervallet [0, 1), kan det bevises at kjøretiden er Theta(n). Se side (fra 222)

26 Side 26 for TDT4120 algdat Cormen: oktober : Minimum og maksimum Minimum Beste måten å finne minste (eller største) verdi i en liste med n elementer, er å kjøre n-1 sammenligninger. Minimum òg maksimum Slik at for å finne minimum (maksimum), brukes Theta(n) tid. Kan finne maksimum og minimum ved å bruke maks 3 * n//2 sammenligninger. Hvordan? Hver sammenligning blir gjort med to elementer av gangen. Først blir de sammenlignet med hverandre, deretter blir det minste elementet sammenlignet med nåværende minimum, og det største elementet med nåværende maksimum. Det vil si at for hvert par med elementer blir det gjort 3 sammenligninger, og dette utføres n // 2 ganger. 9.2 Selection i forventet lineær tid Randomized- Select i gir det i'te minste elementet. Hvis vi for eksempel vil ha det fjerde minste elementet. 1-2: Returnerer elementet hvis det bare er ett element i lista. I så tilfelle er i = 1 [0 i python]. 3: Bruker [quicksorts] Randomized-Partition til å finne tilfeldig oppdeling av lista, slik at alle elementer på plassen før q er mindre enn A[q] og alle etter er større enn a[q]. Se mer om den i kap : k blir satt til å være antallet elementer i A[p..q], altså antall elementer i lista med lavere verdier enn A[q], til og med A[q]. 5-6: Sjekker om antallet elementer i lista stemmer med i-te minste vi vil ha tak i. 7-9: Hvis i < k, så kjøres Randomized-Select på nedre del av lista, ellers kjøres metoden på den øvre delen av lista. Kjøretid Kjøretiden er O(n^2) for verstefall, men har forventet kjøretid Theta(n). Antar:

27 Side 27 for TDT4120 algdat Det er like stor sannsynlighet for alle partisjoner Randomized- Partiotion gjør, der det er n mulige partisjoner, slik at sannsynligheten for at A[p..q] har k elementer er lik 1/n. Definerer: X = Dellisten A[p..q] har nøyaktig k elementer Hvis elementene er distinkte: E[X] = 1/n For lengst mulig tid, antar vi at det i'te minste elementet må ligge i den listen med flest elementer, for flest mulig rekursive kall. Les mer på side (238). Heftig statistikk-greier. Gjerne med penn og papir. 9.3 Selection i verstefalls lineær tid. Hvordan Modifiser Partition-algoritmen fra quicksort til å ta imot elementet lista skal partisjoneres rundt som argument. Da er Select definert slik: 1) Del de n elementene i lista opp i n // 5 grupper, med 5 elementer i hver, der en har n(mod 5) elementer. 2) Finn median til hver av gruppene, ved å bruke innsettsortering, og velge midterste element(er) som median. 3) Bruk Select rekursivt til å finne median x av de ceil(n / 5) medianene funnet i steg 2. Hvis det er partalls antall medianer, blir medianen den laveste, av de to. 4) Partisjoner lista rundt median-av-medianene, x, ved å bruke den modifiserte Partition-metoden. La k være en mer en antall elementer på den nedre siden av partisjonen, slik at x er det k-te minste elementet, og det er n - k elementer på øvre side av partisjonen. 5) Hvis i = k, returner x. Ellers, kall Select rekursivt for å finne det i-te minste elementet på den nedre siden hvis i < k, eller på den øvre siden hvis i > k. Hvorfor fungerer dette? Fordi medianen x garanterer at halvparten av de ceil(n / 5) medianene er større enn x, og hver av de medianene har 2 elementer som er større enn, eller lik. Slik at hver av gruppene med 5 elementer, garanterer at det er 3 elementer som er større enn x, bortsett fra den ene gruppen som har n(mod 5) elementer, og den gruppen som inneholder x selv. Tilsvarende gjelder for elementene som er mindre. Utifra det får man ligninger og greier, som det står mer om på side ( ). Og man får at verstefalls scenario er bundet av O(n) tid. Lurt å lese dette med penn og papir.

28 Side 28 for TDT4120 algdat Cormen: 10.1,2 og august : Stacker og køer Stakk LIFO - last in, first out. Hvis man sletter et element i en stakk, slettes elementet som ble lagt inn sist. Push: Legge inn i en stakk Pop: Fjerne fra stakk Underflows: Hvis vi prøver å poppe en tom stakk. Overflows: Hvis stakk.top er større enn n, der n er antall elementer i stakken. Køer FIFO - first in, first out. Hvis man sletter et element i en kø, slettes elementet som ble lagt inn først. Enqueue: Legge til element i en kø Dequeue: Fjerne element fra en kø Hode: Begynnelsen av køen, der man fjerner elementene. Hale: Slutten av køen, der man legger til elementer 10.2 Lenkede lister (singel) Lenkede lister Dobbelt lenkede lister Sortert lenket liste Rund, lenket liste Legge inn et element i en liste Dataen er arrangert i en lineær rekkefølge, der rekkefølgen er bestemt av en peker i hvert objekt. Har bare en peker til neste objekt. En lenket liste, der hvert objekt har en peker til forrige og neste objekt, i tillegg til en attributt nøkkel. Hvis neste = null, er objektet det siste i lista (halen), og hvis forrige = null, er det det første i lista (hodet). En attributt, head, peker til første element i lista, og hvis head = null, så er lista tom. Den lineære rekkefølgen korresponderer til rekkefølgen til objektenes nøkkel, der det minste elementet er hodet og det største er halen. Halens neste element, neste, peker til hodet, og hodets forrige element, peker til halen. Blir lagt inn på starten av listen. Man redefinerer naboskap:

29 Side 29 for TDT4120 algdat Legge inn et element i en liste Fjerne et element fra en liste Hvis man har en referanse til et objekt x, i en lenket liste, redefinerer man naboskap til forrige og neste element, slik at de peker til hverandre i stedet. Dette tar tid O(1). Hvis man ikke har en referanse, må man først søke listen etter objektet man ønsker, og da tar det O(n) tid. Sentinels Man legger til et objekt på starten av lista, kalt null, som gjør resten av koden lettere. Hodet's forrige peker til dette objektet, og halens neste. Objektet har alle egenskaper bortsett fra en nøkkel. Da trenger man heller ikke en referanse til hodet, for man kan referere til null.neste. Bør ikke brukes hvis man har mange må lister. Gjør nytte hvis vi vil redusere konstant tid Rotfestede trær Oppbygging Binært tre N-tre Tre med tilfeldig antall barn Hver node har referanser til barn, forelder og nøkkel. Har referanser til left, right, p, som tilsvarer venstre barn, høyre barn og forelder (parent). Når man refererer til treet, refererer man til T.root, som tilsvarer roten til treet. Hvis root = Null, så er treet tomt. I et n-tre har hver forelder maksimalt n barn. Dette kan implementeres på samme måte som et binær tre, men med pekere til barn_1, barn_2,,barn_n i stedet for left og right. Hvis man vil ha et tilfeldig antall løv, kan det implementeres med "left-child, right-sibling"-representasjon. I stedet for å lage n veldig stor, og bruke masse unødvendig minne. Andre representasjoner Da har hver node en peker til forelder, p, og T.root peker på treets rot. Forelder har en peker til venstre barn, left, og barn har peker til høyre søsken, right_sibling. Hvis node x ikke har noen barn, er x.left = Null og hvis x er barnet lengst til høyre for sin forelder, er x.right_sibling = Null. Kan representeres med heap, kap 6.

30 Side 30 for TDT4120 algdat Cormen: , Hash-tabeller LES MER PÅ DETTE 4. september : Direkte adressetabeller Direkte adressetabeller Man har en liste, array, tabell, T, med U (antall mulige nøkler) plasser, som korresponderer til u nøkler. Hver nøkkel er unik. Plass k peker på et element med nøkkel k. Hvis det ikke finnes noen nøkkel k, så er T[k] = Null. I noen applikasjoner kan man lagre selve elementet og ikke bare en peker/referanse til elementet. Direkte adressetabeller vs. Hashtabeller Metoder Det er ikke alltid nødvendig å lagre nøkkelen, for hvis vi har indeksen til et objekt i tabellen, så har vi nøkkelen. Hvis vi ikke har nøkler, må vi ha en måte å si om plassen i tabellen er tom. I en direkte adressetabell har man et univers av nøkler som er mulig å adressere - vi har altså en veldig stor tabell, med potensielt få plasser som er i bruk til enhver tid. En hash-tabell er dynamisk i den forstand at tabellen hele tiden har like mange plasser som den har nøkler. Hver metode tar O(1) tid. Fin illustrasjon 11.2 Hash-tabeller Direkte adressetabeller vs. Hash- I en direkte adressetabell har man et univers av nøkler som er mulig å adressere - vi har altså en veldig stor tabell, med potensielt få plasser som er i bruk til enhver tid. En hash-tabell er dynamisk i den forstand at tabellen hele tiden en

31 Side 31 for TDT4120 algdat tabeller Hash-tabeller, og direkte adressering Hash-funksjon Kollisjon Chaining En hash-tabell er dynamisk i den forstand at tabellen hele tiden en størrelse relativ til antall nøkler. Med direkte adressering er et element med nøkkel k lagret i plass k. Med hashing er elementet med nøkkel k lagret i plass H(k). Med andre ord: Vi bruker en hash-funksjon h til å finne plassen til nøkkel k. Hash-funksjonen H mapper universet U av nøkler til plassene i en hash-tabell, T[0 m-1] Der størrelsen på hash-tabellen som regel er mye mindre enn U. Et element med nøkkel k hashes til plass H(k). H(k) er hash-verdien til nøkkelen k. Det kan være at to nøkler hashes til samme plass i tabellen. Siden U > m (m antall plasser i hash-tabell), må det være minst to nøkler som gir samme output. Løsning: Hvis man får H til å virke tilfeldig, kan man minimere antall kollisjoner. En hash-funksjon er ikke tilfeldig, da, siden k må alltid gi samme h(k). Løsning: Chaining Alle elementer som blir hashet til samme plass blir lagt til i en lenket liste, der plassen i hash-tabellen refererer til hodet til lista. Metoder: Analyse av hashing med kjeding / chaining Enkel uniform hashing Innsetting tar O(1) tid, hvis vi tar utg.punkt i at x ikke allerede er i lista. Ellers må vi søke for å sjekke først, og da tar det lenger tid. Verstefalls scenario ved søk er proporsjonalt med lengden på lista. Hvis lista er dobbelt lenket, tar det O(1) tid å slette et element. Ellers må vi først søke etter x, endre koblingen mellom x's forgjenger fra x til x's etterkommer. Load factor (lastfaktor?) Lastfaktor a er definert for en hash-tabell T som n/m, der m er antall plasser og n er antall elementer som er lagret i tabellen. Lastfaktor er gjennomsnitts antall elementer lagret i en kjede. Verstefalls scenario: Alle n nøkler hashes til samme plass, slik at vi får en liste med lengde n. Søketid er Theta(n), i tillegg til å regne ut hash-funksjonen. Gjennomsnittsscenario: Avhenger av hvor bra hash-funksjonen distribuerer mengden med nøkler blant de m plassene i tabellen. Det er like sannsynlig at ethvert element blir hashet til hvilken som helst plass. Gjennomsnittscenario:

32 Side 32 for TDT4120 algdat hashing Gjennomsnittscenario: Hvis mislykket søk: Theta(1 + a) Forventet tid for å få et mislykket søk etter nøkkel k, er forventet tid å traversere listen T[h(k)], som har forventet lengde lik a. Hvis vellykket søk: Theta(1 + a) Der 1 er tiden det tar å regne ut h(k) og a er lastfaktor. Se bevis på side 260 (281) 11.3 Hash-funksjoner En god hashfunksjon Betingelser: Nøklene er tilfeldige reelle tall k, uavhengig og uniformt distribuert i intervallet 0 <= k < 1. Funksjon: H(k) = floor(km) Tilfredsstiller enkel uniform hashing, der m er antall plasser. Eksempel der m = 20, graf: Naturlige tall Delemetoden Hash-funksjoner antar at nøkler er naturlige tall. Hvis de ikke er naturlige tall, finner man en måte å tolke dem som naturlige tall. For eksempel kan en string, "pt" bli tolket som et par tall (112, 116) som tilsvarer plassering i ASCII. Utrykt som et radix-128 tall, blir det: (112 * 128) = H(k) = k mod m Der k er nøkkelen og m er antall plasser. Metoden er kjapp. Det er lurt å velge en m som er et primtall, sånn ikke altfor nærme et tall i toerpotens. Hvis vi for eksempel vil at en hash-tabell skal holde circa n = 2000 char-strenger, der hver char har 8 bits, og vi ikke bryr oss om å søke gjennom gjennomsnittlig 3 elementer i et mislykket søk. Da kan vi sette m = 701, som er nærme 2000/3. Gangemetod en Vi vil ikke at m skal være i toerpotens, fordi et eller annet. H(k) = floor( m(ka mod 1)), der (ka mod 1) = ka - floor(ka) LES MER EN GANG

33 Side 33 for TDT4120 algdat en Universal hashing LES MER EN GANG Hvis man velger en fiksert hash-funksjon, kan det være kjipe folk finner ut av hvilken funksjon som brukes, og kan krasje serveren, slik at n nøkler blir hashet til samme plass. Da vil man få en Theta(n) gjennomsnittstid på å hente elementet. Den eneste effektive måten å forbedre situasjonen på er å velge hash-funksjonen tilfeldig på en slik måte at den uavhengig av nøklene som faktisk blir lagret. Teorem 287 Jeg dør 11.4 Åpen adressering Hva er åpen adressering Innsetting På begynnelsen av kjøringen av et program, blir derfor en tilfeldig hash-funksjon valgt, ut i fra en nøye designet mengde med funksjoner. La H være en endelig mengde med hash-funksjoner, som mapper et univers U med nøkler til intervallet {0, 1,, m-1}. Et slikt univers er universalt hvis for hvert par k, l i U, så er antallet hash-funksjoner h i H der h(k) = h(l) er ikke mer enn H / m (m antall plasser i hash-tabellen). Hvert element er lagret i selve plassen i tabellen, og ikke med en referanse til en lenket liste. Hver plass består dermed av et element eller Null. Hash-tabellen kan fylles opp, slik at man ikke kan putte i mer, men ved å ikke ha pekere, frigjøres minne slik at man kan ha større tabeller, som potensielt kan føre til færre kollisjoner og kjappere henting. Innsetting: Hash-funksjonen består i tillegg av en prøve-posisjon. Man sjekker prøveposisjonen, og hvis det allerede er et element der, sjekker man neste, osv, til man finner en tom plass, der elementet blir satt inn, eller til alle posisjoner er sjekket og tabellen er full. Søking: Ved søk bruker man samme metode som ved innsetting, men da leter man etter elementet. Hvis man kommer til en plass med Null, vet vi at elementet ikke kan være i tabellen, for da ville vi funnet det.

34 Side 34 for TDT4120 algdat Søking Sletting Vi kan ikke bare uten videre slette et element ved å erstatte med Null i en slik tabell, da det vil gi feil ved søking. (Hvis vi sletter element i, og vi søker etter et element som ligger på plass i + n). En løsning er å erstatte slettede elementer med en verdi DELETED, i stedet for Null. Da kan vi modifisere innsetting til å se på DELETED som Null, og søking vil fungere som før. Men vi bruker som regel chaining hvis vi skal slette elementer. 271/292

35 Side 35 for TDT4120 algdat Cormen: august : Binære søketrær Effektivt Hva er et binært søketre? Inorder tretraversering Grunnleggende operasjoner tar tid proposjonal med høyden til treet. For et komplett tre (alle foreldre har 2 barn) med n noder, vil slike operasjoner ta Theta(lg n) verste falls tid. Et binært søketre er ordnet som et binært tre, i tillegg til at nøklene er sortert slik: Hvis man har en node x, så er x.key <= x.right.key og x.key >= x.left.key. Traverserer treet rekursivt, slik at node x's venstre undertre blir printet før x, deretter x.key, deretter x's høyre undertre. Det tar Theta(n) tid å traversere en n-node binært søketre, siden metoden kaller seg selv nøyaktig to ganger for hver node - en gan g for venstre og en for høyre node, etter første kall på metoden. Bevis på side 288 (309) 12.2 Querying a binary search tree Søking Søker et binært tre - returnerer Null hvis man ikke finner key, og returnerer x hvis man finner key.

36 Side 36 for TDT4120 algdat Minimum og maksimum Påfølgende og etterfølgende Sjekker k mot x.key, og hvis k < x.key, sjekkes venstre undertre, ellers sjekkes høyre undertre. Ved å følge venstre barn nedover, til det ikke lenger er flere barn igjen, vil man finne minimale verdi. Tilsvarende finner man maksimale verdi ved å følge høyre barn nedover, til man er kommer til noden lengst til høyre. Hvis man vil finne x's etterfølgende eller påfølgende node, trenger man ikke å sammenligne. Finne etterfølger Deler opp i to tilfeller: i) Hvis x's høyre undertre ikke er tomt, så er barnet lengst til venstre x's høyre undertre etterfølgeren til x. j) Hvis x's høyre undertre er tomt og x har en etterfølger y, så er y den laveste forfedern til x, der y's venstre barn også er forfeder til x. Basically: Gå oppover til man finner en node som er venstre barn til en node y. Y er etterfølger. Teorem Tilsvarende med påfølger, men omvendt. Det er mulig å implementere søk, minimum, maksimum, etterfølger og påfølger slik at de kjører med en tid O(h), der h er høyden på treet Innsetting og sletting/fjerning Innsetting K Beveger seg nedover treet og sammenligner med hver node. Avhengig av om K.key er større eller mindre enn x.key beveger K seg enten høyre eller venstre. Inntil x = Null - da har K funnet riktig plass. Har en variabel Y som peker på x's forelder, slik at man kan ordne koblinger mellom K og Y (forelder) riktig.

37 Side 37 for TDT4120 algdat Bruker O(h) tid, der h er høyde på treet. Sletting Skal fjerne en node Z fra et søketre T. Hovedstrategi: Tre hovedtilfeller 1) Z har ingen barn, slik at vi kan fjerne den ved å modifisere forelder til å erstatte z med Null som barn. 2) Hvis Z har ett barn, kan vi fjerne Z ved å heve nivået til Z's barn, og gjøre Z's barn til barn av Z's forelder i Z's sted. 3) Hvis Z har to barn, må vi finne Z's etterfølger y - som må være i Z's høyre undertre - og y må ta Z's plass. Mer beskrivende, fire tilfeller: 1) Hvis Z ikke har et venstre barn, blir z erstattet av sitt høyre barn, som kan være Null. Hvis Z.right = Null, blir det som at Z ikke har noen barn. Eller som at Z har ett barn, det høyre barnet. 2) Hvis Z ikke har et høyre barn, blir z erstattet av sitt venstre barn. 3) Ellers har Z både et venstre og et høyre barn. Da finner vi Z's etterfølger Y, som ligger i Z's høyre undertre, og som ikke har noe venstre barn. Vi skjærer y ut av treet, og: a. Hvis y er Z's høyre barn, erstattes Z med Y, og vi lar Y's høyre barn være. b. Ellers ligger Y i Z's undertre, men er ikke et av barna til Z. Da må vi først erstatte Y med sitt eget høyre barn, og deretter erstatte Z med Y. Transplant For å kunne flytte undertrær, har vi en metode, transplant: Kode for sletting Den erstatter et undertre som barn til sin forelder med et annet undertre. Når Transplant erstatter undertreet rotfestet på node u med en undertre rotfestet på v, blir node u's forelder forelderen til node v's forelder, og node u's forelder får v som barn.

38 Side 38 for TDT4120 algdat Linje 1-4 fikser hvis det er tilfelle 1) eller 2). Linje 5-12 fikser hvis noden har to barn. Finner Z's etterfølger Y, ved å kalle på minimum-metoden. Sjekker om Z ikke er Y's forelder: Hvis: Y's høyre barn får plassen til Y, ved hjelp av Transplant. Z's høyre barn blir satt til å være Y's høyre barn, og Z's høyre barn får Y som forelder. % dette gjøres uansett: Y og Z bytter plass. Y får Z's venstre barn, og barnet får Y som forelder. Teorem Bruker tid lik O(h), der h er høyden på treet. Innsetting og sletting av noder i et binært søketre kan implementeres slik at kjøretid er lik O(h), der h er høyden på treet.

39 Side 39 for TDT4120 algdat Cormen: mandag 2. november Dynamisk programmering Generelt Overlappende problemer Optimaliserings problemer Hvis et problem har overlappende delproblemer, er det ikke nødvendig å løse samme problemer flere ganger. Vi løser i stedet problemet hvis det ikke er blitt løst før, men hvis det er det, så "slår vi opp i en tabell", og finner svaret vi fant tidligere. Det er typisk å bruke dynamisk programmering i optimaliseringsproblem - problemer med mange forskjellige løsninger, men der vi er ute etter den beste med tanke på et eller annet Stangdelingsproblemet Stangdelingsproblemet Osv Gitt en stang med en lengde på n tommer og en tabell med priser p i for i = 1, 2,, n, finn den maksimale inntekten man kan få ved å dele opp stangen i mindre stenger og selge delene. Merk at om prisen p n for en stang med lengde n som er stor nok, trenger man ikke nødvendigvis kutte opp stangen i det hele tatt. En stang med lengde n kan deles opp på 2 n - 1 forskjellige måter, siden på hver "kutteplass" (i tommer fra venstre) kan vi velge å kutte eller ikke kutte, og det er n - 1 "kutteplasser". Hvis så en optimal løsning deler opp stangen inn i k deler, for en eller annen 1 <= k <= n, så vil en optimal dekomposisjon n = i 1 + i i k Av stangen oppdelt med lengder i 1, i 2,, i k gi en korresponderende maksimal inntekt: r n = p i1 + p i2 + + p ik Si så at vi har følgende pristabell: Hvis vi så ser på i = 1, 2,, 10, så vil vi få følgende løsninger for r: R1 = 1 fra løsning 1 = 1 (ingen kutt) R2 = 5 fra løsning 2 = 2 (ingen kutt) R3 = 8 fra løsning 3 = 3 (ingen kutt) R4 = 10 fra løsning 4 = (5 + 5 > 9) R5 = 13 fra løsning 5 = (5 + 8 > 10) R6 = 17 fra løsning 6 = 6 (ingen kutt) R7 = 18 fra løsning 7 = ( > 17) R8 = 22 fra løsning 8 = ( > 20) R9 = 25 fra løsning 9 = ( > 24) R10 = 30 fra løsning 10 = 10 (ingen kutt) Her ser vi på om det er bedre å bruke prisen for gjeldene lengde er best eller om det er bedre å se på ulike oppdelinger. En stang av

40 Side 40 for TDT4120 algdat Rekursiv topdown implementasjon lengde n kan deles i to på n // 2 måter. Mer generelt kan verdiene r n for n >= 1 se slik ut: r n = max(p n, r 1 + r n - 1, r 2 + r n - 2,, r n r 1 ) Der første argument tilsvarer ingen kutt i det hele tatt, og de resterende tilsvarer å kutte opp stangen i mindre deler, for så å finne optimaliseringen av de. Vi kan også se på det slik: Vi kutter stangen opp i to, men den første delen skal ikke kuttes opp mer. = max ( + ) Hvorfor blir dette riktig? Blir vel fordi hvis r n ikke trenger å kuttes opp, så må den bestå av en allerede optimal del, altså deler som vil gi best optimalisering uten å kuttes videre. Dette problemet har en optimal substruktur: En optimal løsning til et problem som inneholder optimale løsninger til relaterte delproblemer, som vi kan løse på egenhånd. p er en liste med priser [1,, n] og n er et heltall (lengden). 1-2: Returnerer 0 hvis lengden er 0. 3: Initialiserer q riktig slik at max blir regnet riktig senere. 4-5: finner den maksimale verdien av alle oppdelinger av q, der den ene delen kuttes og den andre ikke. Hvorfor er denne treig? Den gjør samme jobb flere ganger. Hvis n = 4, vil den i linje 5 kjøres for n = 3, 2, 1, 0. Når den kjøres for n = 3, vil linje 5 teste n = 2, 1, 0 Dette er SAMME PROBLEM som for n = 4 ahmagawd. Detta tar tid, si.

41 Side 41 for TDT4120 algdat Kjøretid på denne forferdelige algoritmen: T(n) = 2 n Dynamisk programmering Ikke så rart - denne metoden sjekker eksplisitt alle 2 n - 1 måter å kutte opp en stang på. ER LØSNINGEN YEAH. Dette kan forbedres til polynomisk tid. Første fremgangsmåte: Top-down med memoisasjon Vi løser problemet på samme måte som tidligere, men vi sjekker om vi har løst delproblemet før, og i så fall kan vi hente resultatet fra en liste/hash tabell. Vi sier at den rekursive prosedyren er memoisert - vi "husker" resultatet gjort tidligere. Andre fremgangsmåte: Bottom-up metoden Vi sorterer delproblemene etter størrelsene, og løser dem i stigende rekkefølge. Hvis vi så løser et spesielt problem, så har vi dermed allerede løst de mindre delproblemene. Hvert delproblem blir løst bare én gang. Avhenger ofte av størrelse på en eller annen måte. Disse to metodene har samme asymptotiske kjøretid, men det kan skje at den første faktisk ikke sjekker alle mulige delproblem. Bottom-up-metoden har ofte mye bedre konstanter, siden det er lite metodekall. Under er top down-metoden med stangdelingseksempelet: Denne er ikke veldig annerledes fra den tidligere, men den har en ekstra liste r, med tidligere lagrede resultater. Bottom up-metoden:

42 Side 42 for TDT4120 algdat Tar inn to argumenter, p en liste med priser, og n lengden på stangen. 1-2: Definerer listen med maksimal inntekt, r, og setter r[0] til : Finner beste optimalisering av alle lengder j = 1 til n 5-7: Ved å sammenligne ulike oppdelinger av j, og lagre den beste oppdelingen i r[j]. 8: Returnerer r[n]! Kjøretid Kjøretiden i begge versjonene er Theta(n 2 ). Delproblemgraf Delproblemgraf for n = 4 En delproblemgraf er en rettet der det er en kant fra node x til node y hvis å finne en optimal løsning av x består av å se på en optimal løsning av y. Bottom up-fremgangsmåten går ut på å løse alle x før vi løser y. Vi kan se på dette som en reversert topologisk sortering av grafen. Top down-metoden kan sees på som et "bredde først-søk" av grafen. MER om eksempelet Størrelsen på delproblemgrafen kan hjelpe oss til å finne kjøretiden av den dynamiske programmeringsalgoritmen. Typisk er tiden det tar å regne ut løsningen for et delproblem proposjonal med graden (antallet kanter som går ut av noden) til den korresponderende noden i delproblemgrafen, og antallet delproblem er lik antallet kanter i grafen. Se side 368 (389) for mer om den faktiske løsningen til dette problemet. Der de implementerer koden til også å inneholde størrelsene på oppdelingene Matrisekjedemultiplikasjon Hvor ligger problemet Hvis vi skal multiplisere sammen en kjede med matriser, har det mye å si hvilke matriser som multipliseres sammen først.

43 Side 43 for TDT4120 algdat Kjøretiden til denne algoritmen bestemmes av linje 8 - hvor mange skalar multiplikasjoner som gjøres. Linje 8 vil bli utført A.rows * B.columns * A.columns ganger. Eks: Si at vi har en kjede med tre matriser, (A1, A2, A2), som er hhv. 10x100, 100x5 og 5x50-matriser, som skal multipliseres sammen. - Hvis vi multipliserer dem sammen slik: (A1 * A2) * A3 Vil vi gjøre 10*100*5 + 10*5*50 = skalarmultiplikasjoner - Hvis vi derimot multipliserer dem sammen slik: A1 * (A2 * A3) Vil vi gjøre 10*100* *5*50 = skalarmultiplikasjoner DET ER TI GANGER SÅ MANGE!! Vi vil derfor se på den optimale parenteseringen av matrisene, slik at vi gjør minst mulig skalarmultiplikasjoner. Å telle antall parenteser Dynamisk programmering Merk at vi faktisk ikke gjør multipliseringen, vi bare finner ut den beste rekkefølgen å multiplisere. P(n) er antall mulige parenteseringer: 1 = 1 ( ) = ( ) ( ) 2 Det kan vises at denne er Theta(2 n ), altså det vokser eksponentielt. 1) Struktur Litt sånn forhåndsgreier: Vi har produktet A i..j, der i <= j, og dette kommer fra å se på produktet til A i A i+1 A j. For parentesering, må vi dele opp matrisene mellom A k og A k+1 for en k i intervallet [i, j). Dvs. for en eller annen verdi k må vi først regne ut matrisene A i..k og A k+1..j og deretter multiplisere dem sammen for å få det endelige produktet A i..j. Kostnaden for dette er kostnaden å multiplisere sammen A i..k pluss A k+1..j og pluss kostnaden å multiplisere dem med hverandre. Tankegang: Hvis vi deler opp A i A i+1 A j i to deler, ved k, så må den optimale parenteseringen av de to delene også være med i den optimale parenteseringen av A i A i+1 A j. Litt omvendt: Hvis vi har en optimal parentesering av A i A i+1 A j, så må parenteseringen av A i A i+1 A k og A k+1 A k+2 A j inni A i A i+1 A j også være en optimal parentesering av dele alene. Hvorfor? Hvis det fantes en bedre parentesering av delproblemene, kunne vi byttet ut den vi har med den bedre, og få

44 Side 44 for TDT4120 algdat en enda mer optimal løsning. Konklusjon: Vi kan finne en optimal løsning på problemet, ved å dele opp problemet i to, og finne den optimale løsningen til delproblemene. Vi må passe på å sjekke ut alle måter å dele problemet på. 2) Rekursiv løsning La m[i, j] være minimalt antall skalarmultiplikasjoner som trengs for å regne ut A i..j, der A i..j er et delproblem av en kjedemultiplikasjon, 1 <= j <= j <= n. Da er m[i, j] gitt ved: 0 =, = min, + + 1, + < Hvis i = j: Trivielt, dette er samme matrise. Hvis i < j: Det minste av alle partisjoner: Kostnaden å multiplisere sammen A i..k pluss kostnaden å multiplisere sammen A k+1..j pluss kostnaden å multiplisere disse to matrisene sammen. p er i dette tilfellet antall kolonner på hver matrise. Når man skal multiplisere sammen matriser, må antall kolonner på den ene matrisen stemme med antall rader på den andre. Det vil si at p i-1 blir antall rader på matrise A i, fordi matrise A i-1 må ha like mange kolonner som matrise A i har rader. Og hver matrise A i er en p i-1 x p i matrise. Definerer også s[i, j] til å være en verdi k i en optimal løsning, m[i, k] = m[i, k] + m[k + 1, j] + p i-1 p k p j 3) Bottom-up Metoden antar at matrisen A i har dimensjoner p i-1 x p i for i = 1,, n, og tar inn listen [p 0, p 1,, p n ], som har n elementer. Metoden bruker også to hjelpetabeller: m[1..n][1..n] for å lagre m[i, j]-kostnadene. s[1..n-1][2..n] for å lagre s[i, j] i = 1 og j = n (boka bruker i og j, pga. delproblem men forvirrende): Hvis vi skal regne ut et matriseprodukt av n matriser, ser vi bare på kostnaden å regne ut et matriseprodukt av færre enn n matriser.

45 Side 45 for TDT4120 algdat i = 1 og j = n (boka bruker i og j, pga. delproblem men forvirrende): Hvis vi skal regne ut et matriseprodukt av n matriser, ser vi bare på kostnaden å regne ut et matriseprodukt av færre enn n matriser. Dvs.: For k = 1, 2,, n-1, vil matrisen A i..k være et produkt av k < n matriser, og A k+1..j er et produkt av n-k < n matriser. Slik at algoritmen bør fylle inn tabellen m på en måte som tilsvarer å løse parenteseringsproblemet på en matrisekjede av økende lengde. 1-4: Setter n til å være antall matriser, og setter opp de to hjelpetabellene. Setter alle kostnader til 0. 5: Regner først ut kostnaden for delkjeder av lengde 2, deretter av lengde 3 osv. 6-10: Ser så på alle relevante parenteseringer av lengde l. Hvis l = 2, er dette trivielt - da blir alle par matriser ganget med hverandre: A 1..2, A 2..3,, A n-1..n. Hvis l = 3, blir disse parenteseringer sett på: (A i..i+1 )A i+2 og A i (A i+1..i+2 ) Hvis l = 4, blir disse parenteseringer sett på: A i (A i+1..i+3 ) og (A i..i+1 )(A i+2..i+3 ) og (A i..i+2 )A i+3 Osv : Den beste parenteseringen og hvilken k dette gjelder for blir satt i linje Eksempel under

46 Side 46 for TDT4120 algdat 4) Konstruere en Selv om Matrix-Chain-Order-metoden finner optimale antall optimal skalarmultiplikasjon, så viser den ikke direkte hvordan matrisene skal multipliseres sammen. løsning Tabellen S[1..n-1][2..n] gir oss informasjon for dette. Slik at ut i fra k = s[i, j], finner vi beste oppkutting: A i..j = A i..s[1, n] A s[1,n] + 1..n Da kan vi rekursivt finne tidligere matrisemultiplikasjoner, ved å bruke s[1, s[1, n]] og s[s[1, n] + 1, n]. Den følgende metoden printer den optimale parenteseringen, der s er listen med optimale oppkuttinger for alle i, j, og i og j tilsvarer første og siste matrise: 15.3 Elementer i dynamisk programmering Optimal substruktur Et problem har en optimal substruktur, hvis den optimale løsningen til problemet inneholder optimale løsninger til delproblemene.

47 Side 47 for TDT4120 algdat Et mønster i å oppdage en optimal substruktur: 1) Du viser at en løsning til problemet består av å gjøre et valg. Å gjøre dette valget gir ett eller flere delproblem å løse. 2) Du antar at for et gitt problem så blir du gitt valget som vil lede til en optimal løsning. Du er ikke så opptatt av hvordan dette skal gjøres, du bare antar at det er gitt til deg. 3) Gitt dette valget, så bestemmer du hvilket delproblem som følger, og hvordan best karakterisere de gjenværende delproblemene. 4) Du viser at løsningene til delproblemene som er brukt i en optimal løsning av et problem, må selv være optimale, ved å bruke en "kopier og lim inn"-teknikk. Dette gjøres ved å anta at løsningen til hvert delproblem ikke er optimal, og dermed komme med en motsigelse. Hvis du "kutter ut" løsningen som ikke er optimal, og "limer inn" den optimale, så viser du at du kan få en bedre løsning til det originale problemet, og dette motsier antagelsen om at du allerede hadde en optimal løsning. Å karakterisere rommet til delproblemene "To characterize the space of subproblems" Prøv å holde rommet så enkelt som mulig, og deretter utvide, hvis nødvendig. Optimale delstrukturer varierer over domenet på to måter: 1) Hvor mange delproblemer en bruker det originale problemet i sin optimale løsning? 2) Hvor mange valg har vi, når vi skal bestemme hvilke delproblem vi skal bruke i en optimal løsning? Og dette sammen med kjøretid: I stangdelingsproblemet hadde vi Theta(n) delproblem totalt, og maksimalt n valg å gjøre for hvert delproblem. Dette gir en kjøretid på O(n 2 ). I matriseparenteseringsproblemet hadde vi Theta(n 2 ) delproblemer totalt, der hver hadde maksimalt n - 1 valg, som gir en kjøretid på Theta(n 3 ) tid (oppgave ). Uavhengige delproblemer Side (400) Hvis vi skal finne lengste, enkle sti mellom to noder i en graf, så ser vi at dynamisk programmering ikke fungerer. Hvorfor? Fordi problemet har ikke en optimal delstruktur. Hvis vi har en graf som ser slik ut: Da vil lengste enkle vei mellom A og C være A-B-D-C. Men hvis vi ser på A og B, vil lengste veien være A-C-D-B. Altså er ikke delveiene de lengste mulige. Faktisk så ser vi det at lengste vei mellom delveiene A og B og B og D overlapper. Når vi etter å ha funnet lengste vei mellom A og B, skal finne lengste vei mellom B og D, er alle noder brukt, så hvis vi

48 Side 48 for TDT4120 algdat prøver å bruke dem igjen, får vi ikke lenger en enkel vei. Overlappende delproblem Det vil si at delproblemene ikke er uavhengige. Vi må se på hvilke noder vi valgte mellom A og B, når vi skal se på hvilke noder vi kan velge mellom B og D. En annen ingrediens som er viktig for dynamisk programmering, er at ved å løse problemene rekursivt, får vi samme delproblemer, og ikke nye (da ville vi brukt splitt og hersk). Dynamisk programmering benytter seg av at vi kommer til å bruke et delproblem i flere større problem, slik at vi lagrer svaret til delproblemet i en tabell, så kan vi bare slå opp i tabellen når vi trenger det. Rekonstruksjon av en optimal løsning Memoisering Se side 385 (406) for eksempel med matrisemultiplikasjon og splitt og hersk-metode. Når vi bruker dynamisk programmering, bør vi lagre beste løsning en plass, for eksempel i matrisemultiplikasjon, der vi lagret beste oppkutting i tabellen s. Dette sparer oss for mye tid når vi skal rekonstruere løsningen. Vi lager en top down-implementasjon i stedet for en bottom upimplementasjon. Da lagrer vi i stedet hvilke rekursive kall vi har gjort i en tabell, slik at når vi senere gjør samme kall, kan vi bare slå opp i tabellen. Dette vil ha samme asymptotiske kjøretid som bottom up-implementasjonen. Se side 388 (409) for matrisekjedemultiplikasjonsproblemet for top down-implementasjon. Som regel vil en bottom up-implementasjon være mer effektiv med en konstant faktor, siden den ikke har rekursjon, eller trenger å opprettholde tabellen. Vi kan også i noen tilfeller utnytte mønster i tabellen. Alternativt vil memoiseringsløsninger ha den fordelen at de bare løser de nødvendige delproblemene.

49 Side 49 for TDT4120 algdat Cormen: onsdag 11. november Grådige algoritmer En grådig algoritme Velger det som høres best ut der og da Valg av aktiviteter. Problemet Vi har flere aktiviteter som skal bruke samme ressurs, der kun én aktivitet kan bruke ressursen om gangen. For eksempel forelesninger i en forelesningshall. La S = {a 1, a 2,, a n } være mengden med aktiviteter, der hver aktivitet har en starttid s i og en sluttid f i, slik at 0 <= s i < f i < inf. Vi sier at a i og a j er kompatible hvis [s i, f i ) og [s j, f j ) ikke overlapper. Dvs. at f i <= s j eller f j <= s i. I tillegg antar vi at f 1 <= f 2 <= f 3 <= <= f n-1 <= f n (At S er sortert etter sluttid). Fremgangsmåte Vi går fram på samme måte som med dynamisk programmering, men viser at valget kan tas der og da. Dynamisk programmering 1) Optimal La S ij være mengden med aktiviterer som starter etter a i er ferdig, delstruktur og blir ferdig før a j starter. Si at vi vil finne den maksimalt kompatible mengden med aktiviteter i S ij, og at dette er A ij. Anta så at en av a k er med i denne mengden, slik at vi kan dele opp problemet i to: A ik og A kj. = = Det vil si at A ik er snittet av den maksimalt kompatible mengden A ij og alle aktiviteter som slutter før a k begynner. Tilsvarende er A kj snittet av den maksimalt kompatible mengden A ij og alle aktiviteter som begynner etter a k er ferdig. Da er: = { } Og den største mengden A ij består av = aktiviteter. La oss så anta at det finnes en mengde A' ik med flere elementer enn A ik. Dette motsier vår antagelse om at A ij faktisk er den største mengden, fordi da kunne vi bare byttet ut A ik med A' ik. Slik at problemet har en optimal delstruktur. La c[i, j] betegne størrelsen (antall elementer) til A ij. Slik at

50 Side 50 for TDT4120 algdat c[i, j] = c[i, k] + s[k, j] + 1 Hvis vi ikke vet at a k er i den optimale løsningen, så er c[i, j] gitt ved: 0 = Ø, = max {, +, + 1} Ø Whaaat? Da kan vi enten løse den med memoisering, eller en bottom upimplementasjon, men det er en viktig detalj som vi kan bruke. Hva hvis vi kan finne en aktivitet som er med i den endelige løsningen, før vi begynner å løse delproblemene? Si at vi velger den aktiviteten som blir ferdig først, a 1. Vi har s 1 < f 1 og f 1 er den tidligste sluttiden, så ingen andre aktiviteter kan ha en sluttid som er mindre enn, eller lik s 1. Det vil si at alle aktiviteter som er kompatibel med a 1 må starte etter at a 1 er ferdig. Teorem 16.1 Så da kan vi Top down En rekursiv grådig algoritme Videre har vi også sagt at problemet har optimal delstruktur, så la mengden = { : } være mengden med aktiviteter som starter etter at a k er ferdig. Hvis vi gjør det grådige valget med a 1, så er S 1 det eneste delproblemet som gjenstår å løse. Optimal delstruktur forteller oss at hvis a 1 er en optimal løsning, så må den optimale løsningen til problemet bestå av aktivitet a 1 og aktivitetene i den optimale løsningen til delproblemet S 1. Se på et ikke-tomt delproblem S k (= S kn ), og la a m være en aktivitet i S k med den tidligste sluttiden. Da er a m inkludert i en maksimalstørrelse delmengde av kompatible aktiviteter til S k. Bevis side 418 (439) Så selv om vi kan løse problemet med dynamisk programmering, trenger vi ikke det. Vi kan gjentatte ganger velge den aktiviteten som slutter først, og beholde aktivitetene som begynner etter at denne aktiviteten har sluttet. Slik kan vi vurdere hver aktivitet en gang, med monotont økende sluttider. En slik fremgangsmåte kan løses top down. Først velger vi en aktivitet, så løser vi delproblemet. Algoritmen tar inn listen s og f med start- og sluttider, indeksen k som definerer delproblemet S k, og n som er størrelsen til det originale problemet. Den antar at aktivitetene allerede er sortert etter sluttid. 1: Setter m til å være startindeks til aktivitetene vi skal se på. 2-3: Finner aktiviteten i S k som er ferdig først, og som er

51 Side 51 for TDT4120 algdat Kjøretid En iterativ grådig algoritme kompatibel med a k. 4-5: Hvis m er mindre enn, eller lik n, så blir a m lagt til i den optimale løsningen, og et rekursivt kall til delproblemet S m blir gjort. 6: Hvis m er større enn n, er ingen aktiviteter i S k kompatible med a k, og den tomme mengden returneres. Kjøretiden til algoritmen er Theta(n), fordi gjennom alle rekursive kall blir hver aktivitet sett på nøyaktig én gang i while-løkka i linje 2. Metoden tar inn listene s og f med hhv. start- og sluttid. Den antar at aktivitetene er sortert etter stigende sluttid. 1-3: Setter n til å være antall aktiviteter, legger aktiviteten med tidligste sluttid i løsningen (a 1 ) og setter k til å være indeksen til det gjenværende delproblemet. 4-7: Fra 2 og opptil n, så sammenlignes alle aktiviteter med sluttiden til siste aktivitet lagt til i løsningen. Den første aktiviteten som begynner samtidig eller etter siste aktivitet som ble lagt til i løsningen, legges til i løsningen og k oppdateres. 8: Løsningen A returneres. Denne tar også Theta(n) tid, som er lett å se med tanke på forløkka Elementer i grådige algoritmer Prosessen fra forrige kapittel: Ta utgangspunkt i dynamisk programmering Eller: Ta utgangspunkt i en grådig strategi. Grådig valgegenskap 1) Bestem den optimale delstrukturen til problemet. 2) Finn en rekursiv løsning. 3) Vis at hvis vi tar det grådige valget, så vil det bare være ett delproblem igjen. 4) Vis at det er trygt å ta det grådige valget. 5) Finn en rekursiv løsning som implementerer den grådige strategien. 6) Gjør den rekursive løsningen om til en iterativ løsning. 1) Sett opp optimaliseringsproblemet på en slik måte at vi tar et valg, og står igjen med ett delproblem som skal løses. 2) Vis at det er alltid en optimal løsning til det originale problemet som gjør det grådige valget, slik at det grådige valget alltid er trygt. 3) Demonstrer den optimale delstrukturen ved å vise at hvis vi tatt det grådige valget, så gjenstår et delproblem med den egenskap at delproblemet kombinert med det grådige valget er en optimal løsning til det originale problemet. Forskjellen fra dynamisk programmering: Dynamisk programmering er avhengig av resultatene fra delproblemene. Grådige algoritmer er ikke det, og kan se på det beste valget der og da, og deretter løse delproblemene. Dynamisk programmering løser delproblemene, og tar

52 Side 52 for TDT4120 algdat deretter et valg. Grådige algoritmer tar et valg, og løser deretter delproblemene. Beviset til teorem 16.1 illustrerer hvordan dette kan gjøres (men jeg skjønte ikke helt dette beviset, ops ). Optimal delstruktur Grådig algoritme vs. dynamisk programmering Det grådige valget er enklere å ta, hvis vi allerede har noen antagelser om dataen (for eksempel at aktivitetene var sortert etter stigende sluttid). Et problem har en optimal delstruktur, hvis en optimal løsning til problemet inneholder optimale løsninger til delproblemene. Dette er viktig både i grådige algoritmer og dynamisk programmering. Med grådige algoritmer, kan det vises ved at den optimale løsningen til et delproblem sammen med det grådig valget, gir en optimal løsning til et problem. Se på de to problemene (1) 0-1 ryggsekkproblemet og (2) fraksjonsryggsekkproblemet. 1) Vi har en ryggsekk som kan inneholde maksimalt W kg. Vi vil fylle den med ting. Vi kan bare ha ett element av hver ting, og den kan ikke deles. Det blir enten, eller. Hver ting veier w i kg, og har verdi v i. Vi vil ha størst mulig verdi. 2) Vi har en ryggsekk som kan inneholde maksimalt W kg. Vi vil fylle den med ting, men vi kan dele tingene opp, og ta så mye vi orker. Verdien kan være oppgitt i per kg. Vi kan sammenligne dette med gullbarrer, sølvbarrer og bronsebarrer vs. gullstøv, sølvstøv og bronsestøv. Hvis vi har sistnevnte, kan vi se på verdien per kg. Da vil et grådig valg være bra: Vi tar så mye vi kan av gullstøvet. Når det ikke er mer gullstøv, tar vi så mye vi kan av sølvstøvet. Når det ikke er mer sølvstøv, tar vi så mye vi kan av bronsestøvet, til sekken er full. I førstnevnte, er det ikke sikkert dette er mulig. Da kan det være at det er mer gevinst å velge en sølvbarr og en bronsebarr, framfor en gullbarre. Se eksempel under.

53 Side 53 for TDT4120 algdat 16.3 Huffman-koder Huffman-koding Hvis vi skal kode tegn med variabel lengde på bitsene, kan vi bruke Huffman-koding. Vi ser da på frekvensen av tegnene, og gir de tegnene med høyest frekvens kortest lengde på bitsene. Når bitsene har variabel lengde, kan bli vanskelig å skille dem - når slutter det ene tegnet, når begynner det neste? Da kan man bruke prefikskoder - det vil si at et kodeord ikke er prefiks til et annet kodeord. Vi kan bruke et binært tre til å fremstille kodingen for hvert tegn, der hvert tegn tilsvarer hvert løv i treet, og kodingen er stien ned til løvet. Det viser seg at en optimale kode for en fil alltid blir representert av et fullt binært tre (alle interne noder har to barn). I eksempelet under er treet til venstre et eksempel på fast lengdekoding og treet til høyre et eksempel på prefikskoding. Treet til venstre er ikke optimalt, da det ikke er fullt. Treet til høyre er optimalt. Kostnaden til et tre Siden vi derfor bare vil se på fulle binærtre, så vil en optimal prefikskode ha nøyaktig C blader og C - 1 interne noder, der C er mengden med tegn. Gitt et tre T som korresponderer til en prefikskode, kan vi enkelt regne ut antall bits som trengs for å kode en fil. La c være tegn i C, c.freq frekvensen til c i fila og d T (c) dybden til tegnet i treet (lengden av kodeordet). Da er kostnaden til treet gitt ved: ( ) =. ( ) Konstruere et Huffman-tre Koden tar inn en mengde med n bokstaver C.

54 Side 54 for TDT4120 algdat 1-2: Setter n til C og oppretter min-heapen Q, som er "sortert" etter minste frekvens. 3: Oppretter og ordner n-1 interne noder: 4-6: Oppretter en ny node z, og setter barna til å være de to deltrærne med lavest frekvens. 7-8: Setter frekvensen til z til å være summen av frekvensene til de to deltrærne, og setter z tilbake i min-heapen. 9: Returnerer det ene elementet som gjenstår i min-heapen, som er roten til treet. Tar minste frekvens, for vi vil jo ha noden med størst frekvens som rot. Vi bygger på en måte oppover fra nederste nivå. Se eksempel under. Kjøretid Lemma 16.2 Vi antar at Q er implementert som en binær min-heap. Da kan Q initialiseres i O(n) tid, ved å bruke build-min-heap fra 6.3. Løkka i linje 3-8 kjøres nøyaktig n-1 ganger, og hver heapoperasjon krever O(lg n) tid. Slik at løkka legger til O(n lg n) tid til kjøretiden. Slik at total kjøretid til algoritmen blir O(n lg n) tid. Det kan reduseres til O(n lg (lg n)) tid ved å bruke et Emde Boastre. La C være et alfabet der hver bokstav c in C har frekvens c.freq. La x og y være to bokstaver i C som har den laveste frekvensen. Da eksisterer det en optimal prefikskode for C, der x og y har samme lengde og er ulike kun i siste bit. Lemma 16.3 Bevis side 434 (455) La C være et gitt alfabet med frekvens c.freq definert for alle bokstaver c in C. La x og y være de to bokstavene i C med lavest frekvens. La C' være alfabetet C med bokstavene x og y fjernet, og en ny

55 Side 55 for TDT4120 algdat bokstav x lagt til, slik at C' = C + {z} - {x, y}. Definer frekvensen for C' på samme måte som for C, bortsett fra at z.freq = x.freq + y.freq. La T' være ethvert tre som representerer en optimal prefikskode for alfabetet C'. Da representerer treet T en optimal prefikskode for alfabetet C, der T er gitt av T', ved å erstatte løvnoden z med en intern node, og dens barn x og y. Teorem 16.4 Bevis side 435 (456) Prosedyren Huffman gir en optimal prefikskode. Bevis fra lemma 16.2 og 16.3

56 Side 56 for TDT4120 algdat Cormen: september : Representasjon av grafer To måter å repr. Grafer Nabolisterepresentasjon av en graf G = (V, E) 1) En liste/mengde/collection med nabolister Gir en kompakt måte å representere "tynne" grafer, der E <<< V **2 (mange færre kanter enn det hjørner) 2) En nabomatrise Bedre hvis en graf er veldig tett. E er veldig nærme V **2, eller hvis vi må finne fort ut av om det er en kant mellom tom hjørner. Naboliste-representasjon av en graf G = (V, E) består av en array Adj, med V lister - en for hver node i V. Hver liste i Adj, som tilhører kanten v, består av alle andre kanter som er nabo med v. Hvis G er en rettet graf, så er summen av lengden til alle listene lik E (antall kanter). Hvis G er en urettet graf, så er summen av lengden til alle nabolistene lik 2 E. Det trenger Theta(V + E) minne. Ikke kjappere å finne om en kant (u, v) er i grafen, enn å søke etter v i adj[u]. Dette er kjappere i en nabomatrise, men en nabomatrise bruker mer minne. Nabolister Representasjon av veide grafer Nabomatrise Hvis vi har en vektet graf med vekt-funksjon w, kan vi lagre vekten w(u, v) til kanten (u, v) sammen med node v i u's naboliste. En nabomatrise til en graf G = (V, E) består av V rader og kolonner, der hver rad tilsvarer en node. Der plassen A[i][j] sier om det er en kant mellom i og j, ved å være 1 og ellers 0. En nabomatrise trenger Theta(V**2) minne. En nabomatrise i en uretta graf er symmetrisk, A = A**T, det vil si at man noen ganger bare trenger å lagre verdiene over diagonalen (evt under). Trenger kun en bit per entry. Nabomatrise til vektet graf Hvis vi har en vektet graf med vektfunksjon w, kan vi lagre w(u, v) i på A[u][v] og A[v][u]. Hvis plassen er tom kan vi lagre Null, 0 eller infinity Bredde først-søk, BFS Bredde førstsøk Lett å implementere Begynner på en kildenode, k, og oppdager alle noder man kan nå fra k. Finner korteste vei fra k til node x. Lager et bredde først-tre. Bruker O(V + E) tid Kortest vei fra en node s til v, er beskrevet ved delta(s, v): (, ) Bruker farger til å holde styr på noder.

57 Side 57 for TDT4120 algdat Implementasjon Hvite noder er ikke oppdaget. Gråe noder er oppdaget, men kan ha uoppdagede naboer. Svarte noder er oppdaget, og alle dens naboer er oppdaget. Lemma 22.1 FIFO-kø Bruker nabolister La G = (V, E) være en uretta eller retta graf, og s, i V, en tilfeldig node. Da gjelder for enhver kant (u, v) i E: (, ) δ(, ) + 1 Lemma 22.2 Der delta(s, x) betyr korteste sti fra s til x. Den sier at den korteste stien fra s til v må være lik eller kortere enn den korteste stien fra s til u pluss én. Makes sense 8) La G = (V, E) være en retta eller uretta graf, og anta at BFS blir utført på G fra en rotnode s i V. Når søket er ferdig, vil verdien v.distance for hver node v i V være utregna av BFS og tilfredsstille v.distance >= delta(s, v). Lemma 22.3 For å vise at v.distance == delta(s, v) må man se på hvordan køen opererer. Anta at under utføring av BFS på en graf, så består køen Q av hjørnene (v1, v2,, vr), der v1 er hodet av Q og vr er halen. Da gjelder: Korollar 22.4 Teorem: Korrekthet til BFS Så jeg forstår: Vi vil først besøke alle noder på nivå x, der vi legger til alle barn disse nodene kan ha, som vil være på nivå x + 1. Før vi begynner å besøke nodene på nivå x + 1, vil vi ha besøkt alle noder på nivå x, og alle disse vil derfor være fjernet fra køen. Anta at vi og vj er satt i kø under utføring av BFS, og at vi er satt i kø før vj. Da er vi.distance <= vj.distance. La G = (V, E) være en retta eller uretta graf, og anta at BFS blir utført på G fra en gitt rot, s i V. Da vil BFS oppdage alle noder v som kan nåes fra roten s, og ved

58 Side 58 for TDT4120 algdat til BFS Bredde-først trær Lemma 22.6 Da vil BFS oppdage alle noder v som kan nåes fra roten s, og ved terminasjon vil v.distance = delta(s, v) for alle v i V. I tillegg, vil for enhver node v!= s, som kan nås fra s, vil den korteste stien fra s til v være den korteste stien fra s til v.parent, etterfulgt av kanten (v.parent, v) BFS bygger et bredde-først tre når søk blir utført på en graf. Forfeder-delgrafen til G, G[pi] er et bredde først-tre, hvis V[pi] består av nodene som kan nåes fra s, og for alle v i V[pi], så har delgrafen G[pi] en unik, enkel si fra s til v som også er korteste vei fra s til v i G. Når man utfører BFS på en graf G = (V, E), så konstruerer søket pi slik at forfeder-delgrafen G[pi] = (V[pi], E[pi]) er et bredde først-tre. Bevis s. 601 (622) 22.3 Dybde først-søk, DFS DFS Basically: Søker i dybden først. Litt mer: Søker i kanter til nylig oppdagede noder. Når alle nabonoder er oppdaget, backtracker søket til forrige node som ikke har alle kanter oppdaget. Dette fortsetter til alle noder som kan nåes fra den valgte noden er oppdaget. Hvis det er flere uoppdaga noder, velges en av dem som ny rot for søket. Forfeder-delgraf Siden man kan starte søket i flere kilder, kan en nodes forfederdelgraf bestå av flere trær, i motsetning til BDF, der det består av ett deltre. Forfeder-delgrafen, = (V, E ), er derfor definert slik: = {(., ): } Farging Tidsstempel Implementasjon Forfeder-delgrafen lager en dybde først-skog, som består av flere dybde først-trær. Kantene E[pi] er tre-kanter. Samme som i BFS: Hvitt - Uoppdaget Grå - Oppdaget, men med flere uoppdaga naboer Svart - Alle naboer er ferdig oppdaget. Hver node har også et tidsstempel. Første tidsstempel, v.d beskriver når v først ble oppdaget (farget grå), og andre tidsstempel, v.f, beskriver når v ble ferdig prosessert (alle nabonoder er ferdig, v er farget svart). Nyttig for å beskrive oppførsel til DFS. Kan være heltall mellom 1 og 2 V. For enhver node v, vil v.d < v.f (altså discovery-stempel er mindre enn finishing-stempel)

59 Side 59 for TDT4120 algdat Implementasjon Merk Kjøretid Egenskaper Parentesteorem Teorem 22.7 Korollar 22.8 Går gjennom alle noder i G.V. Hvis en hvit node blir funnet, traverseres den med DFS-Visit, og den blir roten til et nytt DFS-tre. Når hver node v i Adj[u] blir prosessert, sier vi at kant (u, v) blir oppdaget av DF-søket Resultatene til et DF-søk avhenger av hvilken rekkefølge nodene blir undersøkt i, i linje 5 DFS, og hvilken rekkefølge DFS-visit besøker naboene til en node i linje 4. I praksis skaper ikke besøksrekkefølgene problemer. DFS-visit: Theta(E) DFS: Theta(V + E) Strukturen til DFS-trærne speiler de rekursive kallene, DFS-visit, gjort på grafen. Eller: u = v.pi hvis og bare hvis DFS-visit(G, v) ble kalt når naboene til u blir undersøkt. Eller: v er en etterkommer av u, hvis og bare hvis v ble oppdaget da u var grå. Oppdagelses- og avslutningstid (discovery og finishing) har en parentes struktur. Hvis oppdagelsen av u blir representert med (u, og avslutningen av u blir representert med u), vil parentesene være ordentlig nøstet (dette gir mening i hodet mitt) I ethvert DF-søk av en graf G = (V, E), for alle par u, v, vil nøyaktig én av disse tre betingelsene holde: Intervallene [u.d, u.f] og [v.d, v.f] er disjunkte, og verken u eller v er en etterkommer av den andre i DFS-treet. Intervallet [u.d, u.f] er tillukket av intervallet [v.d, v.f], og u er en etterkommer av v i DFS-treet. Intervallet [v.d, v.f] er tillukket av intervallet [u.f, u.f] og v er en etterkommer av u i DFS-treet. Bevis s. 608 (629) Nøsting av etterkommeres intervaller Node v er en (proper) etterkommer av node u i en graf, hvis og bare hvis u.d < v.d < v.f < u.f

60 Side 60 for TDT4120 algdat Hvit sti-teorem Teorem 22.9 Klassifikasjon av kanter Farger kan indikere kanttype Teorem Proper descendant - etterkommer av en node, som ikke er noden selv. I en DFS-skog til en graf G = (V, E) er node v en etterkommer av u hvis og bare hvis det finnes en sti fra u til v som består kun av hvite noder, når søket oppdager u ved tiden u.d. Bevis s. 608 (629) Trekanter er kanter i DFS-skogen G[pi]. Kant (u, v) er en trekant hvis v først ble oppdaget ved å utforske kanten (u, v). Bakoverkanter er de kantene (u, v) som kobler en node u til en forfader v i et DFS-tre. (selv-)løkker blir sett på som bakoverkanter. Foroverkanter er de ikke-trekanter (u, v) som kobler en node u til en etterkommer v i et DFS-tre. Krysskanter er alle andre kanter. De kan koble sammen noder i samme DFS-tre, så lenge den ene ikke er en etterkommer av den andre, eller koble sammen noder til forskjellige DFS-trær. Hvit indikerer trekant. Grå indikerer bakoverkant. Svart indikerer foroverkant eller krysskant. En kant (u, v) Foroverkant: u.d < v.d Krysskant: u.d > v.d Oppgave I et DF-søk av en urettet graf G, er hver kant i G enten en trekant eller en bakoverkant. Bevis s. 610 (631) 22.4 Topologisk sortering DAG Topologisk sortering Directed acyclic graph, retta asyklisk graf. En topologisk sortering av en dag, g = (V, E) er en lineær ordning av alle noder slik at hvis G inneholder en kant (u, v), så kommer u før v i ordningen. Kan ikke inneholde sykler. Bruker Theta(V + E) tid Lemma foran i en liste. Det vil si at siste ferdige node blir satt foran alle andre, og første ferdige node kommer bakerst. En retta graf G er asyklisk hvis og bare hvis et DF-søk av G ikke gir bakoverkanter Sterkt sammenhengende komponenter Sterkt sammenhengende graf Sterke komponenter Finne sterke komponenter En retta graf er sterkt sammenhengende hvis det går en vei fra a til b og en vei fra b til a, for alle par noder a og b i grafen. Hvis dette ikke gjelder, er grafen svakt sammenhengende. En sterk (sammenhengende) komponent av en rettet graf er de største delgrafene som er sterkt sammenhengende. For å finne sterke komponenter, transponeres G, til G T = (V, E T ). Det vil si at alle kanter (u, v) i E er reversert, (v, u) i E T.

61 Side 61 for TDT4120 algdat Implementasjon For at to noder a og b skal nås fra hverandre i G må de også nås fra hverandre i G T. Komponent graf En komponentgraf består av sterke komponenter C1, C2,, CR, som kan bli sett på som "egne noder". Komponentgrafen er en DAG. Lemma Lemma La C og C' være distinkte sterkt sammenhengende komponenter i i en retta graf G = (V, E). La u, v i C, og u', v' i C', og anta at G inneholder en sti fra u til u'. Da kan ikke en sti fra v' til v også eksistere. La C og C' være distinkte, sterkt sammenhengende komponenter i en retta graf, G = (V, E). Anta at det er en kant (u, v) i E, der u i C og v i C'. Da er f(c) > f(c') f(x) gir finishing time til siste ferdiggjorde node i komponent X. Korollar Basically: Ved å finne sterke komponenter i en graf, finner man også en topologisk sortering av komponentene. Bevis side 618 (639) La C og C' være distinkte, sterkt sammenhengende komponenter i en rettet graf G = (V, E). Anta at det er en kant (u, v) i E T, der u i C og v i C T. Da er f(c) < f(c') Altså alle kanter i G T som går mellom forskjellige sterke komponenter, går fra en komponent med en tidligere avslutningstid til en med en senere avslutningstid. Hvorfor algoritmen fungerer Bevis s. 619 (640) Korollar forklarer hvorfor algoritmen for å finne sterkt sammenhengende komponenter fungerer. Når vi kjører DFS på G T, så passer vi på å velge noder med synkende avslutningstid. Korollaret impliserer at det ikke kan finnes noen kanter fra en sterk komponent med høyest avslutningstid til en sterk komponent med lavere avslutningstid. Det vil si at det første DFS-treet vi lager ikke kan ha kanter til andre sterke komponenter (eller trær) fordi det har høyest avslutningstid, og dette gjelder for n-te tre i DF-søket. Teorem med bevis om dette på side 619 (640).

62 Side 62 for TDT4120 algdat Cormen: Spenntrær 15. september : Finne et minimalt spenntre Minimale spenntre Generisk metode Hvis man har en graf G = (V, E), så er et spenntre til G et tre som spenner over alle noder i V. Anta at vi har en sammenhengende, uretta graf G = (V, E) med vektfunksjon w: E -> Relle tall. Definisjoner: Et kutt (S, V- S) Kryssing Lett kant Respects Teorem 23.1 Korollar 23.2 A er en mengde med kanter fra G, som hele tiden former et spenntre. Kanter som er "safe" for A, vil si kanter som kan legges til, slik at kantene i A fortsatt former et spenntre. Et kutt (S, V - S) til en uretta graf G er en partisjon av V. En kant krysser kuttet (S, V - S) hvis den går mellom en av nodene i S til en av nodene i V - S. En kant er en lett kant som krysser hvis den har minst vekt av alle kanter som krysser kuttet. Det kan være flere enn én. Et kutt respekterer en mengde A med kanter, hvis ingen kanter i A krysser kuttet. La G = (V, E) være en sammenhengende, uretta graf med en reell funksjon w definert på E. La A være en delmengde av E, som blir inkludert i et minimum spenntre for G, og la (S, V-S) være ethvert kutt av G som respekterer A, og la (u, v) være en lett kant som krysser (S, V - S). Da er (u, v) trygg for A. Bevis s. 627 (648) La G = (V, E) være en sammenhengende, uretta graf med en funksjon w på E som gir reelle tall. La A være en delmengde i E, og som er inkludert i et minimalt spenntre for G. La C = (Vc, Ec) være en sammenhengende komponent (tre) i skogen Ga = (V, A). Hvis (u, v) er en lett kant som kobler C til en annen komponent i Ga, så er (u, v) trygg for A Kruskal og Prim

63 Side 63 for TDT4120 algdat Kruskals algoritme Mengden A er en skog, der hjørnene er de fra grafen G. Den trygge kanten lagt til i A er alltid den letteste kanten som kobler sammen to distinkte komponenter. Hver mengde inneholder hjørnene til et tre i the current forest. Find-Set(u) returnerer et representativt element fra mengden som inneholder u. To noder u, v ligger i samme mengde (samme tre) hvis hvis Find-Set(u) == Find-Set(v). 2-3 lager mengder (trær) for alle noder v i G. 5 Går gjennom kantene fra lettest vekt og oppover. 6-7 hvis to endepunkt i kantene ikke er i samme mengde, blir kant (u, v) lagt til i A, og den nye mengden blir unionen av mengden med u og den med v. Kruskal Kjøretid Prims algoritme Kommer an på hvordan den disjunkte datastrukturen til mengdene blir implementert. Noe med heuristiske.. Side 633 (654) Mengden A former ett enkelt tre. Den trygge kanten lagt til i A er alltid den letteste kanten som kobler et hjørne i treet til et hjørne som ikke er i treet. Starter i en tilfeldig rot, og vokser, til alle noder er koblet til treet. Bruker en min-prioritetskø. Alle noder som ikke er i A er i køen, med en nøkkel-attributt slik at nøkkelen er den letteste vekten til en kant som er koblet til noden og en node i A. Hvis det ikke finnes noen slik kant, er v.nøkkel = evig. Pi er forelder til noden.

64 Side 64 for TDT4120 algdat Prim Kjøretid setter nøkkel til hver node til evig, bortsett fra roten r.key = 0, slik at den prosesseres først. - 7 identifiserer en node u i Q med en lett kant som krysser kuttet (V - Q, Q), og legger den til i V - Q, og dermed (u, u.pi) til i A oppdaterer nøkkel- og forelderattributtene til alle noder ved siden av u, men ikke i treet. Ved å bruke min-hauger, kan det ta O(V lg V + E lg V) = O(E lg V) tid. Ved å bruke fibonacci-hauger, kan dette reduseres til O(V + E lg V). Se side 636 (657)

65 Side 65 for TDT4120 algdat Cormen: oktober : Korteste vei Kortest vei-vekt delta(u, v) I et kortest vei-problem er vi gitt en veid, rettet graf, G = (V, E), med vektfunksjon w: E -> Reelle tall. Vekten w(p) av stien p = (v0, v1,, vk) er summen av vektene på kantene: (v0, v1) + (v1, v2) + + (vk-1 + vk) Hva kan vi bruke korteste vei-algoritmer til? En korteste sti fra node u til node v er derfor definert som en sti med vekt w(p) = w((v,, u)) = delta(u, p). Vi ser på single-source korteste vei-problemer: Gitt en graf G = (V, E), vil vi finne den korteste stien fra en gitt kildenode s i V til alle noder v i V. Dette kan vi bruke til å løse: Enkel-destinasjon korteste-vei problem: Finn en kortest vei til en gitt destinasjon, node t, fra alle noder v. Reverserer alle kanter, og bruker single source. Optimal substruktur Enkelt-par korteste-vei problem: Finn den korteste veien fra u til v, for gitte noder u og v. Ved å løse single-source fra node u, løser vi også dette problemet. Alle-par korteste-vei problem: Finn den korteste veien fra u til v for alle par noder, u og v. Kan løses ved å kjøre single-source på alle noder, men finnes en mer effektiv måte å gjøre dette på. Korteste-vei algoritmer regner med at en korteste vei mellom to noder, også inneholder korteste veier "inni" veien. Lemma 24.1 Gitt en vektet, rettet graf G = (V, E) med vekt funksjon w: E -> R. Negativt vektede kanter La p = (v0, v1,, vk) være en korteste vei fra node v0 til vk, og for enhver i og j slik at 0 <= i <= j <= k, la p[ij] = (vi, vi+1,, vj) være delstien av p fra node vi til node vj. Da er p[ij] korteste vei fra vi til vj. Grafer kan ha negativt veide kanter, og også negative sykler. Hvis en sti har negative sykler, kan den ikke ha en korteste vei. Den korteste veien blir da definert til å være negativt uendelig.

66 Side 66 for TDT4120 algdat Korteste vei fra : delta(s, a) = 3 delta(s, a) = w(s, a) = 3 delta(s, c) = w((s, c)) = w((s, c, d, c)) = = 5 Uendelig mange muligheter på grunn av sykelen, men siden w(c, d) + w(d, c) = 6-3 = 3 > 0, så er korteste vei (s, c). delta(s, e) = w((s, e, f, e)) = w((s, e, f, e, f, e)) = = - uendelig Siden w(e, f) + w(f, e) = 3-6 = -3 < 0, finnes ingen korteste vei. Merk at delta(s, e) = delta(s, f) = delta(s, g) = - uendelig, fordi alle inneholder en negativ sykel. Merk også at siden det ikke finnes noen vei fra s til h, i eller j, er delta(s, h) = delta(s, i) = delta(s, j) = uendelig, til tross for at i, h og j danner en negativ sykel. Sykler Dijkstras algoritme antar at alle vekter er positive. Bellman Ford godtar negative vekter. Vi har sett at en kortest-vei ikke kan bestå av negative sykler. Vi vet også at hvis veien består av en positiv sykel, får vi en kortere vei ved å fjerne sykelen, altså kan ikke en kortest-vei bestå av positive sykler. Hvis en kortest-vei består av sykler der vektene summes til å være 0, kan vi fjerne syklene, og den korteste veien vil fortsatt være kortest. Ergo kan vi anta at en kortest-vei ikke har sykler, men er en enkel sti. Representere korteste veier Predecessor subgraph Siden enhver asykliske sti i en graf G = (V, E) består av mest V distinkte noder, består den også av V - 1 kanter. Slik at vi kan redusere oppmerksomheten vår til mest V - 1 kanter. På samme måte som i bredde først-trær, kan man representere noder i en kortest-vei med en attributt Pi, som enten er None eller en annen node. Slik at Pi er en peker til noden som kommer før i stien.

67 Side 67 for TDT4120 algdat Ved utføring av kortest-vei algoritme Ikke unik Relaxation Så viser deg at ved slutten så former G[Pi] et "kortest-vei"-tre, der roten er s, og veien til alle noder som kan nåes fra s er den korteste veien Kortest-vei tre, G' = (V', E'), har disse egenskapene: 1) V' er mengden med vektorer som kan nåes fra s i G. 2) G' former et rotfestet tre med rot s 3) For alle v i V', så er den unike enkle stien fra s til v i G' en kortest vei fra s til v i G. Korteste veier trenger ikke være unike. v.d kalles et korteste vei-estimat. Relaxing går ut på å oppdatere v.d hvis man finner ut at ved å gå fra s til v via u er en kortere vei. Egenskaper med relaxing og korteste vei. Alle algoritmer i kapittelet bruker relaxation, men de bruker det på forskjellige måter. Triangel ulikhet: For enhver kant (u, v) i E, har vi (, ) (, ) + (, ) Øvre grense-egenskap: Vi har alltid v.d >= delta(s, v) for alle noder v i V, og når v.d blir satt til delta(s, v) vil den aldri endres. Ingen sti-egenskap: Hvis det ikke finnes en sti fra s til v, så er alltid v.d = delta(s, v) = uendelig. Konvergensegenskap: Hvis p = (s,, u, v) er en korteste vei i G for noen u, v i V, og u.d = delta(s, u) når som helst før (u, v) blir relaxa, så er v.d = delta(s, v) hele tiden etterpå. Sti-relaxation egenskap: Hvis p = (v0, v1,, vk) er en korteste vei fra s = v0 til vk, og vi relaxer kantene i p i rekkefølgen (v0, v1), (v1, v2),, (vk-1, vk), så er vk.d = delta(s, vk). Denne egenskapen holder uavhengig av andre relaxationsteg som blir gjort, selv om de er blandet med relaxingen av kantene i p. Forløper-delgraf egenskap: Når v.d = delta(s, v) for alle v i V, så er forløperdelgrafen et korteste vei-tre, rotfestet i s Bellman-Ford algoritmen Når bruker vi denne? Hvis kantene kan ha negative verdier. Sier om grafen har negative sykler.

68 Side 68 for TDT4120 algdat Pseudokode 1: Setter alle v.d, v.pi til initialtilstand. 2-4: Itererer over alle kanter i V, og relaxer dem. Gjør dette V - 1 ganger. 5-6: Sjekker om delta(s, v) er større enn delta(s, u) + w(u, v). Dette skal ikke være tilfellet, da de skal være like. Hvis den er større, så må det være en negativ sykel, og False returneres. Ellers returneres True. Kjøretid Lemma 24.2 Algoritmen kjører i O(VE) tid, siden initialiseringen tar Theta(V) tid. Alle de V - 1 rundene i linje 2-4 tar Theta(E) tid og for-løkka i linje 5-7 tar O(E) tid. La G = (V, E) være en vektet, rettet graf med kilde s og vektfunksjon w: E -> R, og anta at G ikke inneholder negative vektsykler som kan nåes fra s. Da vil vi ha v.d = delta(s, v) for alle noder v som kan nåes fra s, etter de V - 1 iterasjonene i for-løkka i linje 2-4. Korollar 24.3 Teorem 24.4 Korrekthet til Bellman-Ford algoritmen Bevis på side 652 (673) La G = (V, E) være en vektet, rettet graf med kildenode s og vektfunksjon w: E -> R, og anta at G ikke inneholder negative vektsykler som kan nåes fra s. Da vil det, for alle v i V, være en sti fra s til v hvis og bare hvis Bellman-Ford avsluttes med v.d < uendelig, når den kjøres på G. La Bellman-Ford kjøres på en vektet, rettet graf G = (V, E) med kilde s og vektfunksjon w: E -> R. Hvis G ikke inneholder negative vekt-sykler som kan nåes fra s, så returnerer algoritmen True Vi har v.d = delta(s, v) for alle noder v i V Forløperdelgrafen er et korteste vei-tre, rotfestet i s. Hvis G inneholder negative vektsykler som kan nåes fra s, så Returnerer algoritmen False. Bevis litt vanskelig, les på dette. Side 653 (674) 24.2 Single-source korteste vei i DAG-grafer DAG Rettet, asyklisk graf Hva? Gjør en topologisk sortering av en DAG, og deretter relaxe kantene i grafen. Dette kan gjøres i Theta(V + E) tid. Alltid veldefinerte korteste vei - kan ikke finnes sykler i

69 Side 69 for TDT4120 algdat Algoritme / pseudokode grafen, og dermed ikke negative sykler. 1: Sorterer grafen topologisk. Theta(V + E) 2: Kjører Initialize-Single-Source, som setter alle d til uendelig, osv. Theta(V) 3-5: Går gjennom alle noder u i topologisk rekkefølge, og relaxer kantene mellom noden u og dens naboer. Theta(V + E) Teorem 24.5 Hva kan dette brukes til? Slik at hele algoritmen tar Theta(V + E) tid. Hvis en vektet, rettet graf G = (V, E) har en kildenode s og ingen sykler, så vil v.d = delta(s, v) for alle noder v i V, og forløperdelgrafen G[Pi] er et kortest vei-tre, ved slutten av kjøring av Dag- Shortest-Path. Med modifikasjoner kan dette brukes til å finne kritisk sti i en graf (sti som tar lengst tid, osv) på to måter: Gjøre kant-vektene negative og kjøre Dag-Shortest-Paths Kjøre Dag-Shortest-Paths, og endre 'uendelig' med ' - uendelig' i linje 2 i Initialize-Single-Source, og '>' med '<' i relax-prosedyren Dijkstras algoritme Hva? Algoritme / pseudokode Kjører single-source korteste vei-problemet på en vektet, rettet graf G = (V, E), der alle kanter er ikke-negative. S er en mengde med noder, der korteste vei fra kilden s allerede er bestemt. Q er en minimum-prioritetskø med nodene i G som er sortert etter d-verdien. Q = V - S. 1-3: Kjører Initialize-Single-Source, setter S til å være en tom mengde, og Q til å være nodene i G. 4-6: Så lenge Q ikke er tom, settes u til å være den noden

70 Side 70 for TDT4120 algdat Grådig algoritme Korrekthet til Dijkstras algoritme Korollar 24.7 Analyse med minst d (fra Q), og u legges til i S. 7-8: Går deretter gjennom alle naboene til u, og relaxer kantene mellom u og naboene. Siden Dijkstras algoritme alltid legger til den "nærmeste" eller "letteste" kanten i V - S, så sier vi at algoritmen er grådig. Hvis man kjører Dijkstras algoritme på en vektet, rettet graf, G = (V, E), med en ikke-negativ vektfunksjon w og kilde s, avslutter algoritmen med u.d = delta(s, u) for alle noder u i V. Se bevis på side 661 (682) Hvis vi kjører Dijkstras algoritme på en vektet, rettet graf G = (V, E), med en ikke negativ vekt-funksjon w og kilde s, så vil forløperdelgrafen G[Pi] være et kortest vei-tre rotfestet i s ved terminasjon. Avhengig av hvordan prioritetskøen er implementert. Se mer på side 662 (683). Ligner på BFS siden S korresponderer til mengden med svarte hjørner i et BF-søk. Ligner på Prims algoritme, med tanke på at begge algoritmene bruker en minimum-prioritetskø.

71 Side 71 for TDT4120 algdat Cormen: oktober :24 25 Alle-par korteste vei Alternativer Matriser Hvis vi kjører en single-source korteste vei algoritme V ganger (en gang på alle noder): Alle vekter er ikke-negative: Dijkstras algoritme: Med min-prioritetskø: O(V 3 + VE) = O(V 3 ) Med binær min-heap implementasjon: O(VE lg V) Forbedring hvis grafen er spredt (få kanter ifht. noder). Med Fibonacci-heap: O(V 2 lg V + VE) Vekter kan være negative: Bellman-Ford: Kjøretid: O(V 2 E) Som på en tett graf blir: O(V 4 ) Antar at nodene er nummerert 1, 2,, V, der n = V. Slik at nabomatrisen W blir en n x n-matriser. Hvis vi har en rettet graf G = (V, E), tilsvarer radene i grafen franoden og kolonnene til-noden. Forløper matrise Predecessor matrix For å løse alle-par korteste vei, trenger vi også en forløpermatrise, PI = (pi ij ) der pi ij er None hvis i = j eller det ikke finnes noen sti fra i til j. Ellers er pi ij forløperen til j på en eller annen korteste vei fra i. Altså hvis node k kommer rett før j på korteste vei fra i til j, så er k forløperen til j. På samme måte som i single-source korteste vei-problemet så er forløpermatrisen et tre rotfestet i i. For alle i in V defineres forløpermatrisen til G for i som G pi, i = (V pi,i, E pi, i ) der:, = { } V pi,i inneholder alle noder j in V hvis det eksisterer en vei fra i til j og i og j ikke er samme node. Se på det som at vi egentlig kjører single-source korteste vei på i, og vi dermed får forløpermatrisen. Ish, =, :, { } E pi, i inneholder alle kanter (<forløper til j>, j), hvis j er en node som ligger i V pi,i og j og i ikke er samme node. Hvis G pi, i er et korteste vei-tre, så vil denne prosedyren printe en

72 Side 72 for TDT4120 algdat korteste vei fra node i til node j: 25.1 Korteste veier og matrisemultiplikasjon Den korte forklaringen Hvis vi har en matrise som representerer naboforhold til grafer, der hver plass i matrisa representerer vekten til veien mellom to noder, kan vi bruke matrisemultiplikasjon til å finne vekten til den korteste veien. Slik at matrisen L (m) viser vekten til veien mellom to noder, med ikke flere enn m kanter. La så L (1) = W = (w ij ) være vekten til en kant mellom to noder. Da vil L (1) * L (1) * * L (1) = L (n - 1) Dynamisk programmering gi vekten til den korteste veien mellom alle noder. For å speede opp prosessen kan vi så gange sammen L (1) * L (1) = L (2) L (2) * L (2) = L (4) Til vi når L (n - 1) 1) Struktur Strukturen til en optimal løsning: Hvis vi har en kortest vei fra node u til node v, må alle delveier av denne være korteste vei fra en node i til en node j, der i og j begge er på den korteste veien fra u til v. Si så at vi har en nabomatrise W = (w ij ), og at vi ser på en korteste vei p fra node i til node j, og anta at p ikke inneholder flere enn m kanter. Hvis vi antar at det ikke eksisterer negative-vekt sykler, så er m endelig. Hvis i = j så har p vekt 0 og ingen kanter. Hvis i og j er distinkte, kan vi dekomponere veien p til Der p' nå kan ha maks m - 1 kanter. Lemma 24.1 sier at p' er en korteste vei fra i til k, så delta(i, j) = delta(i, k) + w kj 2) Rekursiv Den rekursive løsningen til alle-par korteste vei-problemet løsning La så l (m) ij være den minste vekten til en sti fra node i til node j som inneholder ikke flere enn m kanter. Hvis m = 0 er det en korteste vei fra i til j med 0 kanter, hvis og bare hvis i = j:

73 Side 73 for TDT4120 algdat For m >= 1 regner vi ut l ij (m) som minimumet av l ij (m-1) (vekten til en korteste vei fra i til j, som består av ikke flere enn m - 1 kanter, p' = (i k)) og minimumsvekten av enhver sti fra i til j som består av ikke flere enn m-1 kanter, som vi får ved å se på alle mulige forgjengere k til j. Det vil si at vi rekursivt definerer: Hva blir den faktiske korteste vei delta(i, j)? Hvis grafen ikke inneholder negative vekt-sykler, vil det for hvert par i og j, der delta(i, j) < inf, finnes en korteste vei som er enkel og som består av ikke mer enn n - 1 kanter. En sti fra node i til node j med mer enn n - 1 kanter kan ikke ha lavere vekt enn en korteste vei fra i til j (pga sykler). Slik at de faktiske korteste vei-vekter er gitt av: delta(i, j) = l (n - 1) ij = l (n) ij = l (n + 1) ij = 3) "Bottom-up" Regne ut korteste-vei vektene "bottom-up": Har så en matrise W = (w ij ), og nå skal vi regne ut en serie med matriser, L (1), L (2),, L (n - 1), der m = 1, 2,, n - 1 vi har L (m) = (l (m) ij ). Den siste matrisen L (n - 1) inneholder de faktiske korteste vei-vekter. Merk at l ij (1) = w ij for alle noder i, j in V, og derfor er L (1) = W. Algoritmen under tar inn matriser L (m - 1) og W, og returnerer matrisen L (m). Altså utvider den korteste vei regnet ut så langt med en kant til. Matrisemultiplikasjon 1-2: Lager en ny matrise L' som skal bli L (m). 3-5: Itererer over alle plasser i matrisa, og setter de til å være inf i utgangspunktet. 6-7: Går så gjennom alle noder k, og finner den korteste veien fra k til j. k tilsvarer kolonnene i matrise L. Hvordan tilsvarer dette matrisemultiplikasjon? Hvis vi ønsker å regne ut C = A * B, der A, B er to n x n-matriser, så vil vi for i, j = 1, 2,, n regne ut:

74 Side 74 for TDT4120 algdat Hvis vi så erstatter inf med 0. får vi samme Theta(n 3 )-tid prosedyre for matrisemultiplikasjonen: (Dette kan vi) Da inneholder matrisen L (n - 1) = W (n - 1) de korteste vei-vektene. Følgende prosedyre regner ut denne i Theta(n 4 ) tid: (Legg merke til navnet). Se eksempel under. Tror de bare ignorerer inf.

75 Side 75 for TDT4120 algdat Få det kjappere Vi er ikke interessert i alle matriser, men i matrise L (n - 1). Det er mulig å regne ut L (n - 1) med bare ceil[ lg(n - 1) ] matriseprodukter, ved å regne ut: Siden 2 ceil[ lg(n - 1) ] >= n - 1, vil det siste produktet være lik L (n - 1). Følgende prosedyre gjør det slik: 25.2 Floyd-Warshall

76 Side 76 for TDT4120 algdat Antagelser Dynamisk programmering tenkemåte Kan ha negative vekter, men antar at det ikke finnes negative sykler. 1) Struktur Annerledes enn ved matrisemultiplikasjons-måten. Ser på nodene i mellom endenodene i en sti. Så hvis vi har stien p = (v 1, v 2,, v l ) er vi interessert i nodene i mellom: {v 2,, v l-1 }. Hvis vi antar at nodene i G er V = {1, 2,, n}, så ser vi på en delmengde {1, 2,, k} av noder for en eller annen k. For alle par noder i, j in V, se på alle stier fra i til j, der alle nodene i mellom kommer fra {1, 2,, k}, og la p være den enkle minimumsvektstien i mellom dem. Floyd-Warshall algoritmen ser på stien p og den korteste veien fra i til j med alle noder i mellom, i mengden {1, 2,, k - 1}. Da har det noe å si om k er en del av stien p eller ikke (ikke endepunkt). Ikke i mellom: Da finnes alle mellomnoder i i stien p i mengden {1, 2,, k - 1}. Da er korteste vei fra i til j med alle mellomnoder i {1, 2,, k - 1} også korteste vei fra i til j med alle mellomnoder i mengden {1, 2,, k}. I mellom: Da kan vi dekomponere p inn i Lemma 24.1 sier at p1 og p2 er korteste veier fra hhv. i til k og k til j, og vi kan si at alle mellomnoder i p1 og p2 er fra mengden {1, 2,, k - 1}. Rekursiv løsning Denne er annerledes enn ved matrisemultiplikasjon. La d ij (k) være vekten til en korteste vei fra i til j, der alle mellomnoder er i mengden {1, 2,, k}. Når k = 0, vil en sti fra i til j med ingen mellomnoder nummerert høyere enn 0, ikke ha noen mellomnoder i det hele tatt, og d ij (0) = w ij. d ij (k) blir derfor rekursivt definert: ( ) = 0 = ( ) ( ) ( ) min, + 1 Andre linje: Ser om vekten som allerede er definert, er mindre, eller om det er bedre å gå via noden k.

77 Side 77 for TDT4120 algdat Fordi, for enhver sti vil alle mellomnoder være i mengden {1, 2,, n}, og matrisen D (n) = (d ij (n) ) gir det endelige svaret: "Bottom-up" ( ) = (, ), Basert på rekurrensen kan vi bruke følgende bottom-up metode for å produsere verdiene d ij (k) for økende verdier av k. Kjøretid Konstruere en korteste vei 1-2: Setter n lik antall rader og D (0) til å være matrisen W. 3-4: Regner ut for alle D (k), der D (k) blir satt til å være en ny matrise i hver runde. 5-7: Ser hva som er best for alle veier: å beholde gamle korteste vei, eller å gå innom node k. Bestemt av de tre nøstede løkkene. Alle utførelser i linje 7 tar O(1) tid, så kjøretiden blir Theta(n 3 ). Algoritmen er tett, så konstanten er liten, slik at algoritmen vil fungere bra for passelig store innputt. Flere måter å gjøre dette på: EN MÅTE: Først regne ut D-matrisen, så konstruere forgjengermatrisen PI ut i fra D-matrisen. EN ANNEN MÅTE: Konstruere forgjengermatrisen samtidig som vi regner ut D (k). Da regner vi ut en sekvens med matriser, PI (0), PI (1),, PI (n), der PI = PI (n). Da definerer vi pi ij (k) som forgjengeren til j på den korteste stien fra node i til node j, der alle mellomnodene er i mengden {1, 2,, k}. Da kan pi ij (k) defineres rekursivt. Hvis k = 0, vil en korteste sti fra i til j ikke ha noen mellomnoder i det hele tatt, slik at: ( ) = = = < For k > 0: ( ) ( ) π = ( ) π ( ) ( ) ( ) + ( ) ( ) ( ) > + Den gjør litt det samme som når vi regner ut korteste vei-vekta. Setter gamle forgjenger, hvis det er best, ellers så velger den forgjengeren som går via k.

78 Side 78 for TDT4120 algdat Se på det stooore eksempelet under: Transitiv tillukning Gitt en retta graf G = (V, E), med noder V = {1, 2,, n}, ønsker vi kanskje å bestemme hvorvidt G inneholder en sti fra i til j for alle nodepar i, j in V. Da definerer vi en transitiv tillukning av G som grafen G* = (V, E*), der E* = { (i, j) det eksisterer en sti fra i til j i G.} En måte å løse dette på i Theta(n 3 ) tid, er å gi en vekt 1 til alle kanter i E, og deretter kjøre Floyd-Warshall algoritmen. Hvis det finnes en sti fra i til j, vil d ij < n, ellers vil d ij = inf. En annen måte å løse dette på, som også tar Theta(n 3 ) tid, er å erstatte operasjonene: Min -> OR + -> AND For i, j, k = 1, 2,, n definerer vi t ij (k) til å være 1 hvis det eksisterer en sti fra i til j med mellomnoder i mengden {1, 2,, k} og 0 ellers.

79 Side 79 for TDT4120 algdat Deretter konstruerer vi den transitive tillukningen G* = (V, E*) ved å legge til kant (i, j) inni E* hvis og bare hvis t ij (n) = 1. En rekursiv definisjon av t ij (k) er ganske analog til den for d ij (k) : ( ) 0 (, ) = 1 = (, ) Og for k >= 1: ( ) ( ) ( ) ( ) = Altså den er lik 1 hvis det eksisterer en sti fra i til j fra k = k - 1, eller hvis det eksisterer en sti fra i til j som går via k. 1-2: Setter n til å være antall noder, og lager en n x n- matrise, T (0). 3-7: Setter plass ij til å være 1 hvis det er en kant mellom i og j eller i = j, ellers : Går gjennom fra k = 1 til n, og lager en ny T-matrise tilhørende k : Setter at det finnes en vei fra i til j, hvis det fantes en vei fra i til j for tidligere k, eller hvis det finnes en vei fra i til j via k. 13: Returnerer. HVORFOR BRUKE DETTE OG IKKE FLOYD-WARSHALL? Denne bruker også Theta(n 3 ) tid, men ofte går det raskere å for en datamaskin å bruke logiske operatorer framfor aritmetiske operasjoner. I tillegg krever denne metoden mindre plass, siden det bare opereres med boolske verdier og ikke heltall. Eksempel under:

80 Side 80 for TDT4120 algdat

81 Side 81 for TDT4120 algdat Cormen: fredag 30. oktober Maksimum flyt Hva? Når vi har en grense for hvor mye som kan gå gjennom en komponent. For eksempel i et kretsnettverk Flytnettverk Definisjon på Et flytnettverk, G = (V, E) er en rettet graf der flytnettverk Hver kant (u, v) har en ikke-negativ kapasitet c(u, v) >= 0. Hvis (u, v) i E, finnes ikke en reversert kant i E. Hvis (u, v) ikke i E, er c(u, v) = 0 Selv-løkker er ikke tillatt. Et flytnettverk har en kilde (s, source) og en avgrunn (t, sink). Vi antar at for alle v i V så finnes det en sti fra s til t via v. Grafen er sammenhengende. Siden hver node som ikke er s har minst én inngående kant, så er E >= V - 1 Definisjon på flyt La G = (V, E) være et flytnettverk med kapasitetsfunksjon c. La s være kilden til nettverket og t være avgrunnen. En flyt i G er en funksjon f: V x V -> R som tilfredsstiller disse to egenskapene: Kapasitetsbegrensning: For alle u, v i V må 0 <= f(u, v) <= c(u, v). Flytkonservering: For alle u i mengden V - {s, t} må (, ) = (, ) Når (u, v) ikke i E, kan det ikke være noen flyt fra u til v, og f(u, v) = 0 Vi kaller den ikke-negative kvantiteten f(u, v) for flyten fra node u til node v. Verdien f av en flyt er definert som: = (, ) (, ) Med andre ord, den totale flyten ut av en kilde minus flyten inn i kilden. Dette er så enkelt som å summere flyten til selve kilden. Antiparallellitet Så hvis det er to kanter ut av s med flyt 5 og 6 og en kant inn til s med flyt 1, blir f = = 10 Når vi modellerer virkelige problem hender det at vi får grafer med parallelle kanter, altså en løkke mellom to noder, eller på en annen måte: Både (u, v) og (v, u) er i E. Løsningen blir å legge til en node v' og erstatte kanten (u, v) med (u, v') og (v', v), der disse kantene har samme kapasitet som (u, v). Dvs. c(u, v) = c(u, v') = c(v', v).

82 Side 82 for TDT4120 algdat Eksempel under, mellom (v1, v2): Nettverk med flere kilder og avgrunner. Når vi modellerer den virkelige verden, kan det være vi får flere kilder og avgrunner. Løsningen på dette problemet, blir å legge til en superkilde s som går til alle kilder s1, s2,, sn, der c(s, s1) = = c(s, sn) = uendelig. Tilsvarende gjøres med en superavgrunn t. Alle t1, t2,, tm går til t, der c(t1, t) = = c(tm, t) = uendelig Ford-Fulkerson-metoden Metoden Restkapasitet Residual capacity Anta at vi har et flytnettverk G = (V, E) med kilde s og vask t. La f være flyten i G. Hvis vi ser på et par kanter u, v i V, så definerer vi restkapasiteten cf(u, v) med: c(u, v) - f(u, v) hvis (u, v) i E. f(u, v) hvis (v, u) i E. 0 ellers Dette er restkapasiteten til kantene i Gf (eller Ef). Si det går en kant (u, v) i G. Da tenker vi at det finnes to kanter i Gf, nemlig (u, v) og (v, u), og de får restkapasitet: cf(u, v) = c(u, v) - f(u, c) fordi (u, v) finnes i E.

83 Side 83 for TDT4120 algdat cf(v, u) = f(u, v) fordi (v, u) finnes ikke i E, men (u, v) finnes. Siden vi har antatt at hvis (u, v) i E, så er (v, u) ikke i E, vil nøyaktig ett tilfelle av dette gjelde for alle ordnede par med noder. Med andre ord: Hvis vi har en kant (u, v) med c(u, v) = 15 og en flyt f(u, v) = 9 kan vi øke flyten med c(u, v) - f(u, v) = 15-9 = 6 før vi går over kapasiteten til kanten. Hvis vi i stedet ønsker å returnere flyten fra v til u, blir cf(u, v) = f(v, u) = 9. Restnettverk Residual network Hvis vi så har et flytnettverk G = (V, E) og en flyt f, så er restnettverket til G indusert (forårsaket) av f, G f = (V, Ef), der = (, ) : (, ) > 0 Altså alle kanter som har c f (u, v) > 0 fra det originale nettverket, er med i restnettverket. Se tegningen: Til venstre er flytnettverket, og til høyre er restnettverket. Legg merke til at kapasiteten fra s til v1 er 16 og flyten er 11. Til høyre i restnettverket ser vi så at vi kan øke flyten fra s til v1 med 5, og vi kan minske flyten med 11. Legg også merke til at kapasiteten fra v4 til v3 er 7 og flyten er 7. Det fører til at det i restnettverket går en kant fra v3 til v4 som sier hvor mye vi kan minske flyten med, men ingen kant fra v4 til v3, siden det ikke er mulig å øke flyten mer i den kanten. Dette fører til at Ef <= 2* E Et veikart Legg merke til at en kant med flyt og kapasitet i det originale nettverket, gir to kanter i restnettverket, hvis ikke c(u, v) = f(u, v). Vi kan bruke et restnettverk som et "veikart" for å legge til flyt i det originale flytnettverket. Hvis f er en flyt i G og f' er en flyt i det korresponderende nettverket G f, definerer vi f ^ f' til å være augmenteringen (økningen) av flyt f med f' til å være en funksjon V x V til R definert slik: ( )(, ) = (, ) + (, ) (, ) (, ) 0 Vi både øker og minsker flyten. Altså: Vi øker flyten på kant (u, v) med f'(u, v), men minsker den med f'(v, u). Å sende flyt tilbake i restnettverket tilsvarer å minske flyten i

84 Side 84 for TDT4120 algdat Lemma 26.1 det originale nettverket. Hvis vi sender 5 kasser med honning fra u til v, og sender 2 kasser tilbake fra v til u, tilsvarer å bare sende 3 kasser honning fra u til v. La G = (V, E) være et flytnettverk med kilde s og vask t, og la f være flyten i G. La G f være restnettet til G indusert (forårsaket) av f og la f' være flyten til G f. Da er funksjonen f ^ f' definert i ligning over (et veikart) en flyt i G med verdi: f ^ f' = f + f' Augmenterende sti Bevis side ( ) Gitt et flytnettverk G = (V, E) og en flyt f, da er en augmenterende sti en enkel sti fra s til t i restnettverket G f. Vi kan øke flyten på en kant (u, v) i en augmentert sti med opptil cf(u, v) uten å bryte med kapasitetsbegrensningen på enhver kant (u, v) eller (v, u) i det originale flytnettverket. Vi kaller den maksimale mengden som vi kan øke flyten på hver kant i en augmenterende sti p for restkapasiteten til p, gitt ved: ( ) = min (, ) (, ) å } Lemma 26.2 Altså hvis vi vil øke flyten på en sti i et flytnettverk, må det finnes en "tilsvarende" augmenterende sti i restnettverket, og økningen er den samme som c f (p). La G = (V, E) være et flytnettverk La f være flyten til G La p være en augmenterende sti i G f. Definer en funksjon f p : V x V -> R med: (, ) = ( ) (, ) å 0 Da er f p flyten i G f med verdi f p = c f (p) > 0 Korollar 26.3 Dette lemmaet sier at f p er en økning av flyten. Den sier noe om hvor mye hver kant på en sti kan økes med. La G = (V, E) være et flytnettverk La f være en flyt i G La p være en augmenterende sti i G f. La f p være definert som ovenfor og anta at vi skal øke f med f p. Da er funksjonen f ^ f p en flyt i G med verdi = + > Kutt av flytnettverk Et kutt (S, T) av et flytnettverk G = (V, E) er en partisjon av V til S og T = V - S, slik at s in S og t in T.

85 Side 85 for TDT4120 algdat Hvis f er en flyt, så er nettflyten f(s, T) over kuttet (S, T) definert til å være: (, ) = (, ) (, ) Altså summen av flyten til alle kanter som går fra S til T minus summen av flyten til alle kanter som går fra T til S. Kapasiteten til kuttet (S, T) er (, ) = (, ) Altså summen av kapasiteten til alle kanter som går fra S til T. Minimumkuttet til et nettverk er et kutt der kapasiteten er den minste av alle kutt i nettverket. Viktig å merke seg at kapasiteten blir regnet ut for alle kanter som går fra S til T, mens flyten blir regnet som alle kanter fra S til T minus alle kanter fra T til S. Eksempel på kutt: c(s, T) = c(v1, v3) + c(v2, v4) = = 26 f(s, T) = f(v1, v3) + f(v2, v4) - f(v3, v2) = = 19 Lemma 26.4 La f være en flyt i et nettverk G med kilde s og vask t. La (S, T) være et hvilket som helst kutt av G. Da er nettflyten som krysser (S, T) lik f(s, T) = f Korollar 26.5 Bevis på side 722 (743) Verdien til enhver flyt f i et flytnettverk G er øvre avgrenset av kapasiteten til ethvert kutt av G. Bevis:

86 Side 86 for TDT4120 algdat Teorem 26.6 Maksimumsflyt minimums kutt-teoremet Basic Ford-Fulkerson algoritme Hvis f er flyten til et flytnettverk G = (V, E) med kilde s og vask t, så er de følgende betingelsene ekvivalente: 1) f er maksimumflyten til G 2) Restnettverket til G f inneholder ingen augmenterende stier. 3) f = c(s, T) for et kutt (S, T) av G. Bevis på side 723 (744) 1-2: Går gjennom alle kanter i G.E, og setter kantens flyt til å være 0. 3: Så lenge det finnes en sti fra s til t i restnettverket G f (en augmenterende sti): 4: Regner ut c f (p), maksimale flyt som kan kjøres gjennom stien. 5-8: Går gjennom alle kanter i stien, og øker dem den maksimale flyten hvis de er i E, ellers så minskes kantene med den maksimale flyten. Når algoritmen er ferdig, vil flyten være den maksimale flyten i flytnettverket. Analyse Avhenger av hvordan linje 3 blir implementert: Hvordan finner vi stien p? Finner stien tilfeldig: Hvis f* er maksimum flyt i et transformert nettverk, så vil while-løkka i Ford-Fulkerson kjøres maksimalt f* ganger, siden flyten vil økes med minst 1 enhet i hver iterasjon. Hvis vi har en datastruktur som korresponderer til grafen G = (V, E), og bruker DFS eller BFS til å finne stien p, vil dette ta O(V + E) = O(E) tid. Da vil hver iterasjon i while-løkka ta O(E), og det gjør også initialiseringen i linje 1-2, slik at kjøretiden til Ford-Fulkerson vil være O(E * f* ). Vet ikke helt om dette er ok skrevet, se side 726 (747). Dette er effektivt hvis f* er liten. Hvis f* er stor kan det ta ganske lang tid. I eksempelet under kan det skje at stien som blir valgt kun fører til en økning lik 1 i hver iterasjon. Dette vil ta tid.

87 Side 87 for TDT4120 algdat Edmonds-Karp algoritme Lemma 26.7 Teorem 26.8 Til slutt Ved å implementere Ford-Fulkerson slik at å finne den augmenterende stien gjøres ved å finne den korteste veien fra s til t i restnettverket (implementert med for eksempel BFS), kan algoritmen kjøres i O(VE 2 ) tid. Denne implementasjonen kalles Edmonds-Karp algoritmen. Hvis Edmonds-Karp blir kjørt på et flytnettverk G = (V, E) med kilde s og vask t, så vil den korteste-vei distansen delta f (s, v) i restnettverket G f øke monotont ved hver flytaugmentering for alle noder v in V - {s, t}. Bevis på side 728 (749) Hvis Edmonds-Karp algoritmen blir kjørt på et flytnettverk G = (V, E) med kilde s og vask t, så vil det totale antallet flytaugmenteringer gjort av algoritmen være O(VE). Bevis side 729 (750) Siden vi kan implementere hver iterasjon av Ford-Fulkerson i O(E) tid når vi finner den augmenterte stien med BFS, vil den totale kjøretiden til Edmonds-Karp algoritmen være O(VE 2 ) Maksimum todelt matching Maksimumtodeltmatching problemet. Gitt en urettet graf G = (V, E), vil en matching være en delmengde av kanter M in E, slik at for alle noder v in V, vil maksimalt én kant i M stå på v. Eller: Kanter som er matchet vil ikke stå på samme node. Fargelegging. Vi sier at en node v in V er matchet av matchingen M, hvis en kant i M er ved siden av v. Ellers er v umatchet. En maksimum matching er en matching med maksimal kardinalitet, dvs. en matching M slik at for alle matchinger M' så vil M >= M'. Å finne en maksimum todeltmatching. I dette kapittelet skal vi se på todelte grafer, altså grafer der nodemengdene kan deles opp i to disjunkte mengder: V = (L) U (R) Ford-Fulkerson: Det er mulig å bruke Ford-Fulkerson til å finne en maksimum matching av en uretta, todelt graf G = (V, E) i polynomisk tid V og E. Vi definerer et korresponderende flytnettverk G' = (V', E') for den todelte grafen G som følgende:

88 Side 88 for TDT4120 algdat La Kilden s og vasken t være nye kanter som ikke allerede er i V, og la V' = (V) U {s, t}. Hvis partisjonen av G er V = (L) U (R), så vil de retta kantene i G' være kantene i E rettet fra L til R, sammen med V nye retta kanter. = {(, ): } {(, ) } {(, ): } Alle kanter som går fra kilden s til nodene i L, og alle kantene fra L til R, og alle kantene fra L til vasken t. Til slutt gir vi enhetskapasitet til alle kanter i E'. Siden alle noder i V har minst én kant ved siden av, så er E >= V / 2. Dermed er E <= E' = E + V < = 3* E Og E' = Theta(E). Lemma 26.9 La G = (V, E) være en todelt graf med nodepartisjon V = L u R, og la G' = (V', E') være dens korresponderende flytnettverk. Hvis M er en matching i G, så finnes en flyt f med heltallsverdier i G' med verdi f = M. Alternativt: Hvis f er en flyt f med heltallsverdier i G', så finnes det en matching M i G med kardinalitet M = f. Teorem Korollar Kjøretid Bevis side 733 (754) Hvis en kapasitetsfunksjon c bare tar heltallsverdier, så har den maksimale flyten f gitt av Ford-Fulkerson-metoden følgende egenskap: f er et heltall. I tillegg vil verdien av f(u, v) være et heltall for alle noder u og v. Bevis er en oppgave. Kardinaliteten til en maksimums matching M i den todelte grafen G er den samme som den maksimale flyten f i det korresponderende flytnettverket G'. Bevis side 735 (756) Siden enhver matching i en todelt graf har en graf som ikke er større enn min(l, R) = O(V), vil den maksimale flyten i G' være O(V). Dermed kan vi finne den maksimale matchingen i en todelt graf i O(VE') = O(VE) tid, siden E' = Theta(E).

89 Side 89 for TDT4120 algdat Cormen: 34.5 fredag 13. november NP-kompletthet Algoritmer i polynomisk tid NP-komplette problemer De fleste problemer vi har sett til nå kjører i O(n k ) tid for en konstant k. De kjører i polynomisk tid. Vi sier at problemer som kan løses i polynomisk tid er lydig eller enkle, og problemer som ikke kan det er ulydige eller vanskelige. Problemer der statusen er ukjent - ingen har funnet en polynomisk tid-løsning for problemene, men ei har noen kunnet bevise at det ikke er mulig. Noen problemklasser Klasse P: Kan løses i polynomisk tid. Klasse NP: De problemer som er verifiserbare i polynomisk tid. Hvis vi blir gitt et forslag til en løsning på et problem, så kan vi sjekke at løsningen er riktig i polynomisk tid. P er i NP. Klasse NPC: Et problem er i NPC hvis det er i NP, og er like "vanskelig" eller "ulydig" som ethvert problem i NP. Exp: Kan løses i eksponentiell tid. R: Problemer som kan løses i endelig tid. Det som er irriterende med disse, er at de ligner på problemer som kan løses i polynomisk tid. Eksempler: Korteste vs. lengste enkle sti. Euler-tur vs. Hamilton-tur: En Euler-tur traverserer hver kant nøyaktig en gang, og kan besøke hver node flere enn en gang. Dette problemet kan løses i O(E) tid. En Hamilton-sykel til en rettet graf er en enkel sykel som inneholder alle noder i V. Problemet om en graf har en Hamilton-sykel er NPkomplett. Beslutningsproblemer Program = Binær streng = Naturlige tall in N. De fleste beslutningsproblemer er ikke løsbare. Beslutningsproblemer = Funksjon fra innputt til ja/nei = binær streng = Naturlige tall in N. Men det er uendelig mange innputt vi kan putte inn, og uendelig mange utputt. NP-problemer Er P lik NP?? Så: Beslutningsproblem er noe i R, der programmer er i noe i N. Derfor er R >> N, og det er mange flere reelle tall enn naturlige tall, så nesten alle problemer er uløselige. Står for ikke-deterministisk polynomial (non-deterministic). Det kan beskrives på følgende måter: Beslutningsproblemer som er løsbare i polynomisk tid via en "heldig" algoritme - en algoritme som alltid gjetter riktig. Beslutningsproblemer med "løsninger" som kan "sjekkes" i polynomisk tid. "Heldige" algoritmer Kalles en ikke-deterministisk modell: Algoritmen gjør gjetninger (resultatet er ofte ja eller nei). Når svaret er ja, kan det bevises, og sjekkes i polynomisk tid. Det magiske: Gjetningene er garantert til å gi svaret ja hvis mulig. I NP-problemer kan vi gjøre et polynomisk antall gjetninger, og derfor kan problemet være løsbart i polynomisk tid. "Kan ikke lage flaks" Generere bevis om løsninger kan være vanskeligere enn å sjekke løsninger.

90 Side 90 for TDT4120 algdat Å bevise at et problem er i NP Hvis P!= NP, så er Tetris i NP - P. Hvorfor? Tetris er i NP-vanskelig, minst like vanskelig som alle problemer i NP. Hvis et problem er NP-vanskelig, så er problemet i NPC, NP-complete. Vi bruker ofte tre teknikker for å bevise om et problem er NPkomplett: 1) Vi ser på problemets beslutningsproblem. Hvis vi for eksempel har et optimaliseringsproblem, så gjør vi det om til et beslutningsproblem, der svaret ofte er ja eller nei. Det er ofte enklere (eller "i hvert fall ikke vanskeligere") å se på beslutningsproblemet enn optimaliseringsproblemet. a. Hvis vi har et optimaliseringsproblem "korteste-vei", så kan vi ha et beslutningsproblem "vei" som sier om vei er kortere enn en konstant k (k kan være antall kanter). 2) Vi kan redusere problem til et annet problem. Hvis vi for eksempel har to problem A og B, og A kan konverteres til problemet B i polynomisk tid, så har vi bevist at A må være minst like "lett" som B. a. Hvis B viser seg å være løsbart i polynomisk tid, må også A være det, fordi vi kunne redusere A til B i polynomisk tid. Hvis vi skal bevise hvor vanskelig et problem er, kan vi gå andre veien. Anta at A er i NP, og at vi kan redusere A til B. Anta så at B kan løses i polynomisk tid - det må implisere at A også kan løses i polynomisk tid, noe som er en motsigelse. Circuit-sat Grammatikk/ språk Lemma ) For å bevise at noe er NP-komplett, trenger vi et problem som allerede er bevist å være NP-komplett. Vi kan bruke krets-etellerannet greiene, der vi har en boolsk kombinatorisk krets som består av AND, OR og NOT innganger. Vi ønsker å se om det finnes boolske innganger slik at utganger blir 1. Hvis vi har et boolsk kombinatorisk uttrykk som består av AND, OR og NOT-porter, finn de inngangene som gir 1 på utgangen, og dermed tilfredsstiller kretsen. En måte å gjøre dette på, er å prøve ut alle kombinasjoner på inngangene, og hvis vi har k innganger, vil dette ta 2 k tid. Som ikke er polynomisk. Dette problemet er bevist å være NP-komplett. Vi har et alfabet S med et endelig antall symboler. Et språk L over S er enhver mengde med strenger lagd av symbolene fra S. S* er alle strenger som kan lages ut av alfabetet. Alle språk L er en delmengde av S*. Hvis,, {0,1} er språk, slik at, så implisererer L P at L P. Så hvis L2 er polynomisk, så er også L1 polynomisk Å bevise NP-kompletthet

91 Side 91 for TDT4120 algdat Lemma 34.8 Hva gjør vi SAT-problem Hvis L er et språk slik at L' <= P L for et språk L' in NPC, så er også L NP-vanskelig. Hvis i tillegg L er i NP, så er L in NPC. Ved å redusere et kjent NP-komplett språk L' til L, så reduserer vi implisitt hvert språk i NP til L. Ved lemma 34.8 gir dette oss en metode for å bevise at et språk L er NP-komplett. 1) Vis at L in NP 2) Velg et kjent NP-komplett språk L'. 3) Beskriv en algoritme som lager en funksjon f som mapper hver instans av x in {0, 1}* av L' til en instans av f(x) av L. 4) Hvis at funksjonen f tilfredsstiller x in L' hvis og bare hvis f(x) in L for alle x in {0, 1} 5) Hvis at algoritmen som regner ut f kjører i polynomisk tid. Hva? Kan vi finne ut om en boolsk formel er i SAT? Betingelser: 1) Formelen har n boolske variabler, x1, x2,, xn 2) Formelen har m boolske operasjoner som tar en eller to innputt og gir ett utputt. 3) Vi antar at formelen ikke har overflødige parenteser, altså at formelen inneholder maksimalt ett par parenteser til hver boolske operasjon. En sannhetstilegning til en boolsk formel Phi er et sett verdier for variablene til Phi, og en tilfredsstillende tilegning er en sannhetstilegning som gjør at formelen blir 1. En formel som har en tilfredsstillende tilegning, er en tilfredsstilt formel, SAT-formel: = {ϕ ϕ er en tilfredsstilt boolsk formel} Teorem 34.9 Bevis teorem Den naive algoritmen for å finne ut om en tilfeldig formel er i SAT kjører 2 n tid, siden den sjekker alle mulige kombinasjoner av sannhetstilegninger. Problemet å finne ut om en boolsk formel er tilfredsstilt er NPkomplett. Hvordan vise det? Vi kan vise det ved å redusere et CIRCUIT-SATproblem til en boolsk formel i polynomisk tid. En måte å gjøre det på, er å bare erstatte hver port i kretsen med sin boolske operasjon. Men hvis utgangsledningene til portene er koblet til to eller flere andre innganger, kan den genererte formelen vokse eksponentielt (husk, to innganger, en utgang). En annen måte å gjøre det på, er å gi hver ledning en variabel, x i, og deretter uttrykke formelen som et produkt av ekvivalenser: = ( )( + )( + ) ( )( )( + )( ) Hver av disse små formlene inni parentesene blir kalt en klausul.

92 Side 92 for TDT4120 algdat Hvorfor er kretsen tilfredsstilt når formelen er tilfredsstilt? Hvis kretsen er tilfredsstilt, så må være ledning i kretsen ha en veldefinert verdi, og utgangen være 1. Hvis vi da gir ledningsvariablene våre disse verdiene, vil hver klausul bli 1, og da må alle bli 1. 3-CNF-SAT Teorem Bevis Dermed har vi bevist at vi kan redusere CIRCUIT-SAT til SAT i polynomisk tid, og da må SAT være NP-vanskelig. Vi begrenser SAT-problemet så det blir enklere å jobbe med. CNF står for conjunctive normal form, som basically er POSform, produkt av summer. (a + b)(a' + b + c') En literal i en boolsk formel er en occurence av en variabel eller dens negativ. En boolsk formel er i 3-CNF hvis hver klausul består av nøyaktig tre distinkte literaler. Problemet å finne ut om en boolsk formel i 3-CNF er tilfredsstilt, er NP-komplett. Vi kan bevise dette ved å redusere SAT til CNF-SAT. Så si at vi har et SAT-problem. 1) Vi lager først et binærtre ut av SAT-problemet, slik at hver logiske operasjon tilsvarer en node, og operasjonen har maksimalt to barn. Dette kan videre tolkes som en krets, der hver variabel er kantene mellom nodene, slik at da kan vi det sette det opp som tidligere, som et produkt av klausuler, med ekvivalenser inni. 2) Nå vil hver klausul inneholde maksimalt tre literaler, siden det vil være maksimalt tre kanter koblet til en node. En "utgang" og to "innganger". For hver av klausulene kan vi sette opp sannhetstabeller, og ta summen av alle 0-mintermene. Ved å ta komplementet til dette uttrykket, vil vi få den originale klausulen i CNF-form (produkt av sum). 3) For å sette dette sammen til slutt, så innfører vi to hjelpevariabler p og q. Vi vil at hver OR-term skal inneholde tre literaler, så hvis OR-termen inneholder 2 literaler, fjerner vi denne og legger til: (<OR-term> + p)(<or-term> + p') Hvis OR-termen inneholder én literal, x, fjerner vi denne, og legger til: (x + p' + q')(x + p' + q)(x + p + q')(x + p + q) Da har vi redusert et SAT-problem til et 3-CNF-SAT-problem. Vi kan bevise at dette tar polynomisk tid: 1) Vi introduserer maksimalt én ny variabel og én ny klausul per boolske operasjon. 2) For hver klausul har vi maksimalt tre literaler, så sannhetstabellen får maksimalt 8 rader. 3) For å gjøre det om fra CNF til 3-CNF legger vi til maksimalt 4 klausuler for hver klausul vi sjekker. Slik at størrelsen av den resulterende formelen er polynomisk i lengde sammenlignet med den originale formelen. Hver av konstruksjonene kan enkelt gjøres i polynomisk tid. Da har vi bevist at SAT <=p 3-CNF-SAT, så 3-CNF-SAT er NPkomplett Klikk-problemet, the clique problem

93 Side 93 for TDT4120 algdat Klikk (clique) En klikk i en urettet graf G = (V, E), er en delmengde V' av V, der hvert par med noder er koblet til en kant i E. Med andre ord er en klikk en komplett delgraf av G. Størrelsen til klikken er antall noder den inneholder. Klikk-problemet er optimaliseringsproblemet å finne den største mulige klikk i en graf. Beslutningsproblemet består av å spørre om det finnes en klikk med en gitt størrelse k i grafen. Formelt: = {(, ): å. } Den naive algoritmen går ut på å liste alle k-delmengder av V, og sjekke om noen av dem er en klikk. Da blir kjøretiden: Ω Teorem Bevis Som er polynomisk hvis k er en konstant. Men generelt kan k være nært V /2, og i så tilfelle er algoritmen superpolynomisk. Klikk-problemet er NP-komplett. Bevise at problemet er i NP: Vi kan verifisere om en løsning av problemet er riktig, ved å gå gjennom alle par noder u, v i V', og sjekke om kanten (u, v) er i E. Hvis vi har en delgraf med n noder, er det n(n-1)/2 par noder å sjekke, så dette tar polynomisk tid. Redusering: Deretter beviser vi at 3-CNF-SAT <=p CLIQUE, som vil bevise at klikk-problemet er NP-vanskelig. Vi begynner med en instans av 3-CNF-SAT. La: = Være en boolsk formel i 3-CNF med k klausuler. For r = 1, 2,, k, vil hver klausul C r ha nøyaktig tre distinkte literaler,,,. Vi skal så konstruere en graf G slik at phi er tilfredsstilt hvis og bare hvis G har en klikk med størrelse k. Vi konstruerer grafen G = (V, E) som følgende. For hver klausul = ( + + ) i phi, plasserer vi en trippel av noder,, inn i V. Vi lager en kant mellom to noder og hvis disse to betingelsene er oppfylt: De to nodene er i forskjellige tripler, det vil si at r!= s Deres korresponderende literaler er konsistente, det vil si at den ene er ikke en negasjon av den andre. Hvis vi for eksempel har: = ( + + )( + + )( + + ) Som tilsvarer grafen:

94 Side 94 for TDT4120 algdat Vi må deretter vise at dette faktisk er en reduksjon: Anta at phi har et tilfredsstillende tilegning. Da vil hver klausul C r inneholde minst én literal,, som gir 1, og hver slik literal korresponderer til en node. Ved å velge én slik sann literal fra hver klausul vil vi få en mengde V' med k noder. Vi sier at V' er en klikk. For ethvert par noder, der r!= s, vil begge korresponderende literaler mappe til 1 ved den gitte tilfredsstillings tilegning, og derfor kan ikke literalene være komplement av hverandre. Derfor, ved konstruksjon av G, vil kanten (, ) være i E. Merk Eventuelt, anta at G har en klikk V' med størrelse k. Ingen kanter i G er koblet til noder i samme trippel, så V' inneholder nøyaktig én node per trippel. Vi kan gi 1 til hver literal slik at uten å tenke på at vi gir 1 til både literalen og dens komplement, siden G ikke inneholder kanter mellom inkonsekvente literaler. Hver klausul er tilfredsstilt, så phi er tilfredsstilt. Enhver variabel som ikke korresponderer til en node i klokken kan settes tilfeldig. Her har vi redusert 3-CNF-SAT til en instans av CLIQUE med en spesiell struktur, og det kan virke som at vi har bevist at klikkproblemet er NP-vanskelig for denne strukturen, men vi har faktisk bevist det for alle strukturer. Hvorfor? Fordi hvis vi hadde hatt en algoritme som kunne løse alle klikk-problemer polynomisk, så hadde den også kunne løse denne strukturen vi har polynomisk. Og gjøre det motsatt, hadde ikke fungert: At vi hadde tatt en spesiell instans av 3-CNF-SAT og redusert den til en generell instans av CLIQUE, fordi det kan være vi hadde tatt en instans av 3-CNF-SAT som er polynomisk! Sånn at jeg forstår dette Merk også at reduksjonen brukte instansen av 3-CNF-SAT, men ikke løsningen. Vi hadde feilet hvis vi reduksjonen hadde vært avhengig av å vite om formelen phi er tilfredsstilbar, siden vi ikke vet hvordan vi kan tilfredsstille phi i polynomisk tid (da hadde heller ikke reduksjonen blitt polynomisk). Jeg har en (vilkårlig) 3-CNF-SAT-formel med k klausuler. Ved reduksjonen forklart ovenfor gjør jeg denne om til en graf. Hvis jeg kan finne en klikk med størrelse k, betyr det at det må finnes en sannhetstilegning som tilfredsstiller 3-CNF-SAT-formelen. Det vil si at ved å løse klikk-problemet, løser jeg også 3-CNF-SATproblemet. Da må klikk-problemet være like vanskelig å løse som 3-CNF-SAT-problemet.

95 Side 95 for TDT4120 algdat Nodedekkingsproblemet Nodedekking Et nodedekke av en urettet graf G = (V, E) er en delmengde V' av V, slik at hvis (u, v) in E, så er u in V' eller v in V' (eller begge). Det vil si at hver node "dekker over" sin påliggende kant, og et nodedekke for G er en mengde med noder som dekker over alle kanter i E. Se eksempel Nodedekke-problemet går ut på å finne det minste mulige nodedekket i en gitt graf. Som beslutningsproblem, blir det "kan vi finne et nodedekke med størrelse k?". Som språk, er det definert slik: Teorem Bevis VERTEX-COVER = {(G, k) : grafen G har et nodedekke med str. k} Nodedekke-problemet er NP-komplett. Bevise at problemet er i NP: Vi har en graf G = (V, E) og et tall k. Vi bruker nodedekket V' in V som et løsningsforslag. Verifikasjonen sjekker at V' = k, og deretter sjekker den for alle kanter (u, v) i E at u eller v er i V'. Dette kan gjøres i polynomisk tid. Reduksjon: Vi kan vise at dette problemet er NP-vanskelig, ved å vise at CLIQUE <=p VERTEX-COVER. Denne reduksjonen ser på tanken om et "komplement" til en graf. Gitt en urettet graf G = (V, E), så definerer vi komplementet til G som G' = (V, E'), der = {(, ):,, (, ) }. Med andre ord er G' grafen som består av de kantene som ikke er i G. I figuren ovenfor ser vi eksempel på dette. Reduksjonsalgoritmen tar som innputt, instansen (G, k) av klikkproblemet. Deretter regner den ut komplementet G', som lett kan gjøres i polynomisk tid. Utputten av reduksjonsalgoritmen er instansen (G', V - k) av nodedekkeproblemet. For å fullføre beviset, så viser vi at denne transformasjonen er en reduksjon: Grafen G har en klikk med størrelse k hvis og bare hvis grafen G' har et nodedekke med størrelse V - k. Anta at G har en klikk V' in V, der V' = k, og at V - V' er et

96 Side 96 for TDT4120 algdat nodedekke i G'. La så (u, v) være en tilfeldig kant i E'. Da er ikke kanten i E, som impliserer at minst én av u eller v ikke tilhører i V', fordi alle noder i V' må være koblet til alle andre noder i V'. Ekvivalent så må minst én av nodene u eller v være i V - V', som betyr at kanten (u, v) er dekket i V - V'. Siden vi valgte kante (u, v) tilfeldig fra E', må alle kanter i E' være dekket av en node i V - V'. Derfor må mengden V - V' med størrelse V - k forme et nodedekke for G'. Eventuelt, anta at G' har et nodedekke V' in V, der V' = V - k. For alle u, v in V vil u eller v (eller begge) være i V' hvis (u, v) er i E'. Moteksempelet til denne implikasjonen er at for alle u, v in V, hvis u eller v ikke er i V', så må (u, v) være i E. Med andre ord er V - V' en klikk, og har størrelse V - V' = k Hamilton-sykel problemet Hamilton-sykel En hamilton-sykel av en urettet graf G = (V, E), er en enkel sykel som inneholder alle noder i V. En graf som inneholder en Hamilton-sykel, er en Hamiltonian. Vi definerer problemet, "Har grafen G en Hamilton-sykel?" som språket: Teorem Bevis Dette beviset er langt og vondt au-au HAM-CYCLE = {G: G er en hamilton-graf} Hamilton-sykel problemet er NP-komplett. Bevise at problemet er i NP: Vi har et løsningsforslag til graf, og skal sjekke om det er en Hamilton-sykel. Dette gjøres ved å sjekke at det finnes en kant mellom alle nodene i G, og at løsningen begynner og slutter med første node slik at det danner en sykel. Dette kan gjøres i polynomisk tid. Reduksjon: Vi skal nå bevise at VERTEX-COVER <=p HAM-CYCLE, noe som beviser at HAM-CYCLE er NP-komplett. Gitt en urettet graf G = (V, E), og et heltall k, konstruerer vi en urettet graf G' = (V', E') som har en Hamilton-sykel hvis og bare hvis G har et nodedekke med størrelse k. For å konstruere denne grafen G', bruker vi noe som heter widget: Hver widget representerer en kant i grafen, og den har visse egenskaper: For hver kant (u, v) in E, så har grafen G' en widget, som vi skriver som W uv. Hver kant i widgeten blir skrevet som [u, v, i] eller [v, u, i] for i = 1, 2, 6, slik at hver widget inneholder 12 noder. I tillegg har widgeten 14 kanter. Se figur under:

97 Side 97 for TDT4120 algdat Kun nodene [u, v, 1], [v, u, 1], [u, v, 6] og [v, u, 6] (hjørnenodene) har koblinger til resten av grafen G'. Enhver hamilton-sykel må traversere kantene på én av de tre måtene vist ovenfor. Den må besøke alle noder, og ingen andre måter å traversere widgeten på vil gjøre det. Hvis den går inn [u, v, 1], må den gå ut [u, v, 6], og tilsvarende hvis den går inn [v, u, 1]. I tilfelle (c) må den besøke widgeten to ganger. Grafen G' består da av en widget for hver kant som er i grafen. I tillegg består grafen av k selector-noder, så bruker vi kantene som står på selector-nodene i G' til å velge de k kantene som former dekket av G. I tillegg består grafen G' av to andre typer kanter som vises i figuren under. Den ene typen: For hver node u i V, så lager vi en sti mellom alle widgeter som inneholder u, som tilsvarer alle noder som står ved siden av u. Vi setter rekkefølgen selv, i eksempelet er den w, x, y, z. Alle noder ved siden av u: u (1), u (2),, u (degree(u)) I eksempelet under (gult), så står nodene x, y, z ved siden av w. Da blir kantene ([w, x, 6], [w, y, 1]) og ([w, y, 6], [w, z, 1]) lagt til i E. Disse kantene kan kombineres til en sti som inneholder alle noder som står ved siden av w. Tanken er at hvis vi velger node u in V fra nodedekket av G, så kan vi konstruere en sti fra [u, u (1), 1] til [u, u (degree(u)), 6] i G' som "dekker" alle widgeter som korresponderer til kanter som står på u. Da inneholder stien alle 12 noder i, ( ) hvis kun u i nodedekket, ellers så inneholder stien 6 av nodene i widgeten hvis både u og u (i) er med i nodedekket.

Heapsort. Lars Vidar Magnusson Kapittel 6 Heaps Heapsort Prioritetskøer

Heapsort. Lars Vidar Magnusson Kapittel 6 Heaps Heapsort Prioritetskøer Heapsort Lars Vidar Magnusson 24.1.2014 Kapittel 6 Heaps Heapsort Prioritetskøer Sorterings Problemet Sorterings problemet er et av de mest fundementalske problemene innen informatikken. Vi sorterer typisk

Detaljer

Quicksort. Lars Vidar Magnusson Kapittel 7 Quicksort Randomisert Quicksort Analyse av Quicksort

Quicksort. Lars Vidar Magnusson Kapittel 7 Quicksort Randomisert Quicksort Analyse av Quicksort Quicksort Lars Vidar Magnusson 29.1.2014 Kapittel 7 Quicksort Randomisert Quicksort Analyse av Quicksort Om Quicksort Quicksort er en svært populær sorteringsalgoritme. Algoritmen har i verstefall en kjøretid

Detaljer

Lars Vidar Magnusson

Lars Vidar Magnusson Binære Søketrær Lars Vidar Magnusson 14.2.2014 Kapittel 12 Binære Søketrær Søking Insetting Sletting Søketrær Søketrær er datastrukturer som støtter mange dynamiske sett operasjoner. Kan bli brukt både

Detaljer

deeegimnoorrrsstt Sjette forelesning

deeegimnoorrrsstt Sjette forelesning deeegimnoorrrsstt Sjette forelesning 1 2 Rebus. Hva er dette? Svar: Kvadratiske sorteringsalgoritmer :-> Som vanlig relativt abstrakte beskrivelser her. Ta en titt på pseudokode i boka for mer detaljert

Detaljer

INF2220: Time 12 - Sortering

INF2220: Time 12 - Sortering INF0: Time 1 - Sortering Mathias Lohne mathialo Noen algoritmer Vi skal nå se på noen konkrete sorteringsalgoritmer. Gjennomgående i alle eksempler vil vi sortere tall etter tallverdi, men som diskutert

Detaljer

n/b log b n = (lg n) a log b n = n log b a

n/b log b n = (lg n) a log b n = n log b a Masterteoremet 1 T (n) = at (n/b) + f(n) Antall «barn»: Størrelse per «barn»: «Høyde»: a n/b log b n = (lg n) Rota har f(n) arbeid; hver løvnode har en konstant mengde arbeid. Hva vil dominere totalen?

Detaljer

Eksamensoppgave i TDT4120 Algoritmer og datastrukturer

Eksamensoppgave i TDT4120 Algoritmer og datastrukturer Institutt for datateknikk og informasjonsvitenskap Eksamensoppgave i TDT0 Algoritmer og datastrukturer Faglig kontakt under eksamen Magnus Lie Hetland Telefon 98 5 99 Eksamensdato 7. desember, 06 Eksamenstid

Detaljer

Først litt praktisk info. Sorteringsmetoder. Nordisk mesterskap i programmering (NCPC) Agenda

Først litt praktisk info. Sorteringsmetoder. Nordisk mesterskap i programmering (NCPC) Agenda Først litt praktisk info Sorteringsmetoder Gruppeøvinger har startet http://selje.idi.ntnu.no:1234/tdt4120/gru ppeoving.php De som ikke har fått gruppe må velge en av de 4 gruppende og sende mail til algdat@idi.ntnu.no

Detaljer

Hashtabeller. Lars Vidar Magnusson Kapittel 11 Direkte adressering Hashtabeller Chaining Åpen-adressering

Hashtabeller. Lars Vidar Magnusson Kapittel 11 Direkte adressering Hashtabeller Chaining Åpen-adressering Hashtabeller Lars Vidar Magnusson 12.2.2014 Kapittel 11 Direkte adressering Hashtabeller Chaining Åpen-adressering Dictionaries Mange applikasjoner trenger dynamiske sett som bare har dictionary oparsjonene

Detaljer

EKSAMEN. Dato: 28. mai 2018 Eksamenstid: 09:00 13:00

EKSAMEN. Dato: 28. mai 2018 Eksamenstid: 09:00 13:00 EKSAMEN Emnekode: ITF20006 Emne: Algoritmer og datastrukturer Dato: 28. mai 2018 Eksamenstid: 09:00 13:00 Hjelpemidler: Alle trykte og skrevne Faglærer: Jan Høiberg Om eksamensoppgavene: Oppgavesettet

Detaljer

Innhold. Innledning 1

Innhold. Innledning 1 Innhold Innledning 1 1 Kompleksitetsanalyse 7 1.1 Innledning.............................. 8 1.2 Hva vi beregner........................... 8 1.2.1 Enkle operasjoner...................... 8 1.2.2 Kompleksitet........................

Detaljer

Heap* En heap er et komplett binært tre: En heap er også et monotont binært tre:

Heap* En heap er et komplett binært tre: En heap er også et monotont binært tre: Heap Heap* En heap er et komplett binært tre: Alle nivåene i treet, unntatt (muligens) det nederste, er alltid helt fylt opp med noder Alle noder på nederste nivå ligger til venstre En heap er også et

Detaljer

Lars Vidar Magnusson

Lars Vidar Magnusson B-Trær Lars Vidar Magnusson 5.3.2014 Kapittel 18 B-trær Standard operasjoner Sletting B-Trær B-trær er balanserte trær som er designet for å fungere bra på sekundære lagringsmedium e.g. harddisk. Ligner

Detaljer

Kap 9 Tre Sist oppdatert 15.03

Kap 9 Tre Sist oppdatert 15.03 Kap 9 Tre Sist oppdatert 15.03 Definere et tre som en datastruktur. Definere begreper knyttet til tre. Diskutere mulige implementasjoner av tre Analysere implementasjoner av tre som samlinger. Diskutere

Detaljer

Studentnummer: Side 1 av 1. Løsningsforslag, Eksamen i TDT4120 Algoritmer og datastrukturer August 2005

Studentnummer: Side 1 av 1. Løsningsforslag, Eksamen i TDT4120 Algoritmer og datastrukturer August 2005 Studentnummer: Side 1 av 1 Løsningsforslag, Eksamen i TDT4120 Algoritmer og datastrukturer August 2005 Faglige kontakter under eksamen: Magnus Lie Hetland, Arne Halaas Tillatte hjelpemidler: Bestemt enkel

Detaljer

Binær heap. En heap er et komplett binært tre:

Binær heap. En heap er et komplett binært tre: Heap Binær heap En heap er et komplett binært tre: Alle nivåene i treet, unntatt (muligens) det nederste, er alltid helt fylt opp med noder Alle noder på nederste nivå ligger så langt til venstre som mulig

Detaljer

Heap og prioritetskø. Marjory the Trash Heap fra Fraggle Rock

Heap og prioritetskø. Marjory the Trash Heap fra Fraggle Rock Heap og prioritetskø Marjory the Trash Heap fra Fraggle Rock Binær heap En heap er et komplett binært tre: Alle nivåene i treet, unntatt (muligens) det nederste, er alltid helt fylt opp med noder Alle

Detaljer

Øvingsforelesning 6. Sorteringsalgoritmer. Kristian Veøy

Øvingsforelesning 6. Sorteringsalgoritmer. Kristian Veøy Øvingsforelesning 6 Sorteringsalgoritmer Kristian Veøy veoy@stud.ntnu.no 26.09.08 1 Spørsmål fra øvingsgruppene Må jeg kunne python på eksamen? (Nei) Er det lurt å gjøre alle programmeringsøvingene? (Ikke

Detaljer

Om Kurset og Analyse av Algoritmer

Om Kurset og Analyse av Algoritmer Om Kurset og Analyse av Algoritmer Lars Vidar Magnusson 8.1.2014 Praktisk informasjon om kurset Hva er en algoritme? (kapittel 1) Hvordan analysere en algoritme? (kapittel 2) Praktisk Informasjon Introduction

Detaljer

Avsluttende eksamen i TDT4120 Algoritmer og datastrukturer

Avsluttende eksamen i TDT4120 Algoritmer og datastrukturer Avsluttende eksamen i TDT4120 Algoritmer og datastrukturer Eksamensdato 14. desember 2011 Eksamenstid 1500 1900 Sensurdato 14. januar Språk/målform Bokmål Kontakt under eksamen Magnus Lie Hetland (tlf.

Detaljer

deeegimnoorrrsstt Sjette forelesning

deeegimnoorrrsstt Sjette forelesning deeegimnoorrrsstt Sjette forelesning 1 2 Bellman-Ford BFS/DFS Binære søketrær Binærsøk Bubblesort Bucket sort Counting sort Dijkstra DAGshortest-path Edmonds- Karp Floyd- Warshall Hashing Heapsort Huffmankoding

Detaljer

... Når internminnet blir for lite. Dagens plan: Løsning: Utvidbar hashing. hash(x) katalog. O modellen er ikke lenger gyldig ved

... Når internminnet blir for lite. Dagens plan: Løsning: Utvidbar hashing. hash(x) katalog. O modellen er ikke lenger gyldig ved Dagens plan: Utvidbar hashing (kapittel 5.6) B-trær (kap. 4.7) Abstrakte datatyper (kap. 3.1) Stakker (kap. 3.3) Når internminnet blir for lite En lese-/skriveoperasjon på en harddisk (aksesstid 7-12 millisekunder)

Detaljer

Pensum: fra boken (H-03)+ forelesninger

Pensum: fra boken (H-03)+ forelesninger Pensum: fra boken (H-03)+ forelesninger unntatt kursorisk tema KAP. 1 KAP. 2 KAP. 3 JAVA I-110 (ikke gjennomgått) OO + ABSTRAKSJON /GENERISK PROGRAMMERING REKURSJON ALGORITME-TIDSANALYSE; O-NOTASJON KAP.

Detaljer

Pensum: fra boken (H-03)+ forelesninger

Pensum: fra boken (H-03)+ forelesninger Pensum: fra boken (H-03)+ forelesninger unntatt kursorisk tema KAP. 1 KAP. 2 KAP. 3 JAVA I-110 (ikke gjennomgått) OO + ABSTRAKSJON /GENERISK PROGRAMMERING REKURSJON ALGORITME-TIDSANALYSE; O-NOTASJON KAP.

Detaljer

Notater til INF2220 Eksamen

Notater til INF2220 Eksamen Notater til INF2220 Eksamen Lars Bjørlykke Kristiansen December 13, 2011 Stor O notasjon Funksjon Navn 1 Konstant log n Logaritmisk n Lineær n log n n 2 Kvadratisk n 3 Kubisk 2 n Eksponensiell n! Trær

Detaljer

Eksamen i tdt4120 Algoritmer og datastrukturer

Eksamen i tdt4120 Algoritmer og datastrukturer Norges teknisk naturvitenskapelige universitet Institutt for datateknikk og informasjonsvitenskap Side 1 av 5 Oppgavestillere: Magnus Lie Hetland Jon Marius Venstad Kvalitetskontroll: Magnar Nedland Faglig

Detaljer

Algdat Oppsummering, eksamen-ting. Jim Frode Hoff

Algdat Oppsummering, eksamen-ting. Jim Frode Hoff Algdat Oppsummering, eksamen-ting Jim Frode Hoff November 18, 2012 1 Definisjoner 1.1 Ordliste Problem Probleminstans Iterasjon Asymtpoisk notasjon O(x) kjøretid Ω(x) kjøretid Θ(x) kjøretid T (x) kjøretid

Detaljer

Algdat Eksamensforelesning. Nils Barlaug

Algdat Eksamensforelesning. Nils Barlaug Algdat Eksamensforelesning Nils Barlaug Eksamen Pensum Eksamen Pensum Oppgaver du har gjort og ting du har lest Eksamen Pensum Oppgave på eksamen Oppgaver du har gjort og ting du har lest Eksamen Pensum

Detaljer

Øvingsforelesning 6. Sorteringsalgoritmer. Martin Kirkholt Melhus Basert på foiler av Kristian Veøy 30/09/14 1

Øvingsforelesning 6. Sorteringsalgoritmer. Martin Kirkholt Melhus Basert på foiler av Kristian Veøy 30/09/14 1 Øvingsforelesning 6 Sorteringsalgoritmer Martin Kirkholt Melhus martme@stud.ntnu.no Basert på foiler av Kristian Veøy 30/09/14 1 Agenda l Spørsmål fra øving 4 l Sortering l Presentasjon av øving 6 30/09/14

Detaljer

Fra Kap.10 Binære søketre (BS-tre) Sist oppdatert 20.03.10 Definere en abstrakt datastruktur binært søketre. Vise hvordan binær søketre kan brukes

Fra Kap.10 Binære søketre (BS-tre) Sist oppdatert 20.03.10 Definere en abstrakt datastruktur binært søketre. Vise hvordan binær søketre kan brukes Fra Kap.10 Binære søketre (BS-tre) Sist oppdatert 20.03.10 Definere en abstrakt datastruktur binært søketre. Vise hvordan binær søketre kan brukes til å løse problemer. Undersøke ulike implementasjoner

Detaljer

Løsningsforslag for Obligatorisk Oppgave 3. Algoritmer og Datastrukturer ITF20006

Løsningsforslag for Obligatorisk Oppgave 3. Algoritmer og Datastrukturer ITF20006 Løsningsforslag for Obligatorisk Oppgave 3 Algoritmer og Datastrukturer ITF20006 Lars Vidar Magnusson Frist 28.03.14 Den tredje obligatoriske oppgaven tar for seg forelesning 9 til 13, som dreier seg om

Detaljer

Sorteringsproblemet. Gitt en array A med n elementer som kan sammenlignes med hverandre:

Sorteringsproblemet. Gitt en array A med n elementer som kan sammenlignes med hverandre: Sortering Sorteringsproblemet Gitt en array A med n elementer som kan sammenlignes med hverandre: Finn en ordning (eller permutasjon) av elementene i A slik at de står i stigende (evt. avtagende) rekkefølge

Detaljer

ALGORITMER OG DATASTRUKTURER

ALGORITMER OG DATASTRUKTURER Stud. nr: Side 1 av 6 NTNU Norges teknisk-naturvitenskapelige universitet BOKMÅL Fakultet for informasjonsteknologi, matematikk og elektroteknikk Institutt for datateknikk og informasjonsvitenskap AVSLUTTENDE

Detaljer

Ekstra ark kan legges ved om nødvendig, men det er meningen at svarene skal få plass i rutene på oppgavearkene. Lange svar teller ikke positivt.

Ekstra ark kan legges ved om nødvendig, men det er meningen at svarene skal få plass i rutene på oppgavearkene. Lange svar teller ikke positivt. Side 1 av 5 Noen viktige punkter: (i) (ii) (iii) (iv) Les hele eksamenssettet nøye før du begynner! Faglærer går normalt én runde gjennom lokalet. Ha evt. spørsmål klare! Skriv svarene dine i svarrutene

Detaljer

Hvor raskt klarer vi å sortere?

Hvor raskt klarer vi å sortere? Sortering Sorteringsproblemet Gitt en array med n elementer som kan sammenlignes med hverandre: Finn en ordning (eller permutasjon) av elementene slik at de står i stigende (evt. avtagende) rekkefølge

Detaljer

Ny/utsatt EKSAMEN. Dato: 6. januar 2017 Eksamenstid: 09:00 13:00

Ny/utsatt EKSAMEN. Dato: 6. januar 2017 Eksamenstid: 09:00 13:00 Ny/utsatt EKSAMEN Emnekode: ITF20006 Emne: Algoritmer og datastrukturer Dato: 6. januar 2017 Eksamenstid: 09:00 13:00 Hjelpemidler: Alle trykte og skrevne Faglærer: Jan Høiberg Om eksamensoppgavene: Oppgavesettet

Detaljer

Algdat-ninja på 60 minutter: Et galskapsprosjekt. Magnus Lie Hetland

Algdat-ninja på 60 minutter: Et galskapsprosjekt. Magnus Lie Hetland Algdat-ninja på 60 minutter: Et galskapsprosjekt Magnus Lie Hetland 15. november, 2002 Advarsel: Tettpakkede og overfladiske foiler forut! 1 Algtdat i 6 punkter 1. Grunnbegreper og basisverktøy 2. Rekursjon

Detaljer

INF Algoritmer og datastrukturer

INF Algoritmer og datastrukturer INF2220 - Algoritmer og datastrukturer HØSTEN 2017 Ingrid Chieh Yu Institutt for informatikk, Universitetet i Oslo Forelesning 4: Prioritetskø og Heap Ingrid Chieh Yu (Ifi, UiO) INF2220 H2017, forelesning

Detaljer

ALGORITMER OG DATASTRUKTURER

ALGORITMER OG DATASTRUKTURER Stud. nr: Side 1 av 7 NTNU Norges teknisk-naturvitenskapelige universitet BOKMÅL Fakultet for informasjonsteknologi, matematikk og elektroteknikk Institutt for datateknikk og informasjonsvitenskap AVSLUTTENDE

Detaljer

ALGORITMER OG DATASTRUKTURER

ALGORITMER OG DATASTRUKTURER Stud. nr: Side 1 av 6 NTNU Norges teknisk-naturvitenskapelige universitet BOKMÅL Fakultet for informasjonsteknologi, matematikk og elektroteknikk Institutt for datateknikk og informasjonsvitenskap LØSNINGSFORSLAG,

Detaljer

Lars Vidar Magnusson Kapittel 13 Rød-Svarte (Red-Black) trær Rotasjoner Insetting Sletting

Lars Vidar Magnusson Kapittel 13 Rød-Svarte (Red-Black) trær Rotasjoner Insetting Sletting Rød-Svarte Trær Lars Vidar Magnusson 21.2.2014 Kapittel 13 Rød-Svarte (Red-Black) trær Rotasjoner Insetting Sletting Rød-Svarte Trær Rød-Svarte trær (red-black trees) er en variasjon binære søketrær som

Detaljer

Divide-and-Conquer II

Divide-and-Conquer II Divide-and-Conquer II Lars Vidar Magnusson 1712014 Kapittel 4 Analyse av divide-and-conquer algoritmer ved hjelp av rekursjonstrær Analyse av divide-and-conquer algoritmer ved hjelp av masterteoremet Løse

Detaljer

Eksamensoppgave i TDT4120 Algoritmer og datastrukturer

Eksamensoppgave i TDT4120 Algoritmer og datastrukturer Institutt for datateknikk og informasjonsvitenskap Eksamensoppgave i TDT0 Algoritmer og datastrukturer Faglig kontakt under eksamen Magnus Lie Hetland Telefon 98 5 99 Eksamensdato 7. desember, 06 Eksamenstid

Detaljer

Dynamisk programmering

Dynamisk programmering Dynamisk programmering Metoden ble formalisert av Richard Bellmann (RAND Corporation) på 50-tallet. Programmering i betydningen planlegge, ta beslutninger. (Har ikke noe med kode eller å skrive kode å

Detaljer

Sortering i Lineær Tid

Sortering i Lineær Tid Sortering i Lineær Tid Lars Vidar Magnusson 5.2.2014 Kapittel 8 Counting Sort Radix Sort Bucket Sort Sammenligningsbasert Sortering Sorteringsalgoritmene vi har sett på så langt har alle vært sammenligningsbaserte

Detaljer

Eksamensoppgave i TDT4120 Algoritmer og datastrukturer

Eksamensoppgave i TDT4120 Algoritmer og datastrukturer Eksamensoppgave i TDT4120 Algoritmer og datastrukturer Faglig kontakt under eksamen Magnus Lie Hetland Tlf. 91851949 Eksamensdato 11. august 2014 Eksamenstid (fra til) 0900 1300 Hjelpemiddelkode D. Ingen

Detaljer

Spenntrær, oppsummert: Kruskal: Traverserer ikke. Plukker kanter i hytt og vær Prim: Legger alltid til den noden som er nærmest treet

Spenntrær, oppsummert: Kruskal: Traverserer ikke. Plukker kanter i hytt og vær Prim: Legger alltid til den noden som er nærmest treet Spenntrær, oppsummert: Kruskal: Traverserer ikke. Plukker kanter i hytt og vær Prim: Legger alltid til den noden som er nærmest treet 1 A B D C Prim: Kruskal: AB, BD, DC DC, AB, BD 2 0 + 1 + + n 1; antall

Detaljer

Dynamisk programmering Undervises av Stein Krogdahl

Dynamisk programmering Undervises av Stein Krogdahl Dynamisk programmering Undervises av Stein Krogdahl 5. september 2012 Dagens stoff er hentet fra kapittel 9 i læreboka, samt kapittel 20.5 (som vi «hoppet over» sist) Kapittel 9 er lagt ut på undervisningsplanen.

Detaljer

Eksamensoppgave i TDT4120 Algoritmer og datastrukturer

Eksamensoppgave i TDT4120 Algoritmer og datastrukturer Eksamensoppgave i TDT4120 Algoritmer og datastrukturer Faglig kontakt under eksamen Magnus Lie Hetland Tlf. 918 51 949 Eksamensdato 12. august, 2014 Eksamenstid (fra til) 0900 1300 Hjelpemiddelkode D.

Detaljer

Alg. Dat. Øvingsforelesning 3. Grafer, BFS, DFS og hashing. Børge Rødsjø rodsjo@stud.ntnu.no

Alg. Dat. Øvingsforelesning 3. Grafer, BFS, DFS og hashing. Børge Rødsjø rodsjo@stud.ntnu.no Alg. Dat Øvingsforelesning 3 Grafer, BFS, DFS og hashing Børge Rødsjø rodsjo@stud.ntnu.no Dagens tema Grafer Terminologi Representasjon av grafer Bredde først søk (BFS) Dybde først søk (DFS) Hashing Hashfunksjoner,

Detaljer

Eksamensoppgave i TDT4120 Algoritmer og datastrukturer

Eksamensoppgave i TDT4120 Algoritmer og datastrukturer Eksamensoppgave i TDT4120 Algoritmer og datastrukturer Faglig kontakt under eksamen Magnus Lie Hetland Tlf. 91851949 Eksamensdato 7. desember 2013 Eksamenstid (fra til) 0900 1300 Hjelpemiddelkode Målform/språk

Detaljer

Kap.12. Flervegssøketre. Studerer 2-3 og 2-4 trær. Sist oppdatert

Kap.12. Flervegssøketre. Studerer 2-3 og 2-4 trær. Sist oppdatert Kap.12 Flervegssøketre Sist oppdatert 12.04.10 Studerer 2-3 og 2-4 trær Motivasjon n maks = antall elementer i et fullt binært tre med nivåer 0 k ; (en node har ett element) n maks = 2 0 + 2 1 + + 2 k

Detaljer

Alg. Dat. Øvingsforelesning 3. Grafer, BFS, DFS og hashing

Alg. Dat. Øvingsforelesning 3. Grafer, BFS, DFS og hashing Alg. Dat Øvingsforelesning 3 Grafer, BFS, DFS og hashing Dagens tema Grafer Terminologi Representasjon av grafer Bredde først søk (BFS) Dybde først søk (DFS) Hashing Hashfunksjoner, hashtabeller Kollisjonshåndtering

Detaljer

EKSAMEN. Dato: 18. mai 2017 Eksamenstid: 09:00 13:00

EKSAMEN. Dato: 18. mai 2017 Eksamenstid: 09:00 13:00 EKSAMEN Emnekode: ITF20006 Emne: Algoritmer og datastrukturer Dato: 18. mai 2017 Eksamenstid: 09:00 13:00 Hjelpemidler: Alle trykte og skrevne Kalkulator Faglærer: Jan Høiberg Om eksamensoppgavene: Oppgavesettet

Detaljer

Repetisjon: Binære. Dagens plan: Rød-svarte trær. Oppgave (N + 1)!

Repetisjon: Binære. Dagens plan: Rød-svarte trær. Oppgave (N + 1)! Repetisjon: Binære søketrær Dagens plan: Rød-svarte trær (kap. 12.2) B-trær (kap. 4.7) bstrakte datatyper (kap. 3.1) takker (kap. 3.3) For enhver node i et binært søketre gjelder: lle verdiene i venstre

Detaljer

Dynamisk programmering

Dynamisk programmering Dynamisk programmering Metoden ble formalisert av Richard Bellmann (RAND Corporation) på 5-tallet. Programmering i betydningen planlegge, ta beslutninger. (Har ikke noe med kode eller å skrive kode å gjøre.)

Detaljer

Ny/utsatt EKSAMEN. Dato: 5. januar 2018 Eksamenstid: 09:00 13:00

Ny/utsatt EKSAMEN. Dato: 5. januar 2018 Eksamenstid: 09:00 13:00 Ny/utsatt EKSAMEN Emnekode: ITF20006 Emne: Algoritmer og datastrukturer Dato: 5. januar 2018 Eksamenstid: 09:00 13:00 Hjelpemidler: Alle trykte og skrevne Faglærer: Jan Høiberg Om eksamensoppgavene: Oppgavesettet

Detaljer

IN Algoritmer og datastrukturer

IN Algoritmer og datastrukturer IN2010 - Algoritmer og datastrukturer HØSTEN 2018 Ingrid Chieh Yu Institutt for informatikk, Universitetet i Oslo Forelesning 3: Prioritetskø og Heap Ingrid Chieh Yu (Ifi, UiO) INF2010 H2018, forelesning

Detaljer

Definisjon av binært søketre

Definisjon av binært søketre Binære søketrær Definisjon av binært søketre For alle nodene i et binært søketre gjelder: Alle verdiene i nodens venstre subtre er mindre enn verdien i noden Alle verdiene i nodens høyre subtre er større

Detaljer

Avsluttende eksamen i TDT4120 Algoritmer og datastrukturer

Avsluttende eksamen i TDT4120 Algoritmer og datastrukturer Avsluttende eksamen i TDT4120 Algoritmer og datastrukturer Eksamensdato 3. desember 2012 Eksamenstid 0900 1300 Sensurdato 3. januar 2013 Språk/målform Bokmål Kontakt under eksamen Magnus Lie Hetland (tlf.

Detaljer

Dagens stoff er hentet fra kapittel 9 i læreboka, samt kapittel 20.5 (som vi «hoppet over» sist)

Dagens stoff er hentet fra kapittel 9 i læreboka, samt kapittel 20.5 (som vi «hoppet over» sist) Dynamisk programmering Undervises av Stein Krogdahl 5. september 2012 Dagens stoff er hentet fra kapittel 9 i læreboka, samt kapittel 20.5 (som vi «hoppet over» sist) Kapittel 9 er lagt ut på undervisningsplanen.

Detaljer

LØSNINGSFORSLAG, EKSAMEN I ALGORITMER OG DATASTRUKTURER (IT1105)

LØSNINGSFORSLAG, EKSAMEN I ALGORITMER OG DATASTRUKTURER (IT1105) Norges teknisk naturvitenskapelige universitet Institutt for datateknikk og informasjonsvitenskap Side 1 av 8 Faglig kontakt under eksamen: Magnus Lie Hetland LØSNINGSFORSLAG, EKSAMEN I ALGORITMER OG DATASTRUKTURER

Detaljer

UNIVERSITETET I OSLO

UNIVERSITETET I OSLO UNIVERSITETET I OSLO Det matematisk-naturvitenskapelige fakultet Eksamen i IN 115 og IN 110 Algoritmer og datastrukturer Eksamensdag: 14. mai 1996 Tid for eksamen: 9.00 15.00 Oppgavesettet er på 8 sider.

Detaljer

INF2220: Forelesning 2

INF2220: Forelesning 2 INF2220: Forelesning 2 Mer om analyse av algoritmer Analyse av binære søketrær Balanserte søketrær Rød-svarte trær (kapittel12.2) B-trær (kapittel 4.7) ANALYSE AV ALGORITMER 2 Analyse av tidsforbruk Hvor

Detaljer

Pensum: 3. utg av Cormen et al. Øvingstime: I morgen, 14:15

Pensum: 3. utg av Cormen et al. Øvingstime: I morgen, 14:15 http://www.idi.ntnu.no/~algdat algdat@idi.ntnu.no Pensum: 3. utg av Cormen et al. Øvingstime: I morgen, 14:15 b c g a f d e h The pitch drop experiment. Foreløpig kjørt fra 1927 til nå. Åtte dråper har

Detaljer

Binære søketrær. Et notat for INF1010 Stein Michael Storleer 16. mai 2013

Binære søketrær. Et notat for INF1010 Stein Michael Storleer 16. mai 2013 Binære søketrær Et notat for INF Stein Michael Storleer 6. mai 3 Dette notatet er nyskrevet og inneholder sikkert feil. Disse vil bli fortløpende rettet og datoen over blir oppdatert samtidig. Hvis du

Detaljer

INF Algoritmer og datastrukturer

INF Algoritmer og datastrukturer INF2220 - Algoritmer og datastrukturer HØSTEN 2016 Ingrid Chieh Yu Institutt for informatikk, Universitetet i Oslo Forelesning 4: Prioritetskø og Heap Ingrid Chieh Yu (Ifi, UiO) INF2220 H2016, forelesning

Detaljer

Grunnleggende Datastrukturer

Grunnleggende Datastrukturer Grunnleggende Datastrukturer Lars Vidar Magnusson 7.2.2014 Kapittel 10 Stakker og køer Lenkede lister Pekere og objekter Trerepresentasjoner Datastrukturer Vi er i gang med tredje del av kurset hvor vi

Detaljer

Algoritmer og Datastrukturer IAI 21899

Algoritmer og Datastrukturer IAI 21899 Eksamen i Algoritmer og Datastrukturer IAI 21899 Høgskolen i Østfold Avdeling for informatikk og automatisering Torsdag 30. november 2000, kl. 09.00-14.00 LØSNINGSFORSLAG 1 Del 1, Binære søketrær Totalt

Detaljer

INF2220: Time 4 - Heap, Huffmann

INF2220: Time 4 - Heap, Huffmann INF0: Time 4 - Heap, Huffmann Mathias Lohne mathialo Heap (prioritetskø) En heap (også kalt prioritetskø) er en type binært tre med noen spesielle struktur- og ordningskrav. Vi har to typer heap: min-

Detaljer

Definisjon: Et sortert tre

Definisjon: Et sortert tre Binære søketrær Definisjon: Et sortert tre For alle nodene i et binært søketre gjelder: Alle verdiene i nodens venstre subtre er mindre enn verdien i noden Alle verdiene i nodens høyre subtre er større

Detaljer

All good things. Fjortende forelesning

All good things. Fjortende forelesning All good things Fjortende forelesning Div notater finnes på http://www.idi.ntnu.no/~algdat Foiler finnes på http://www.idi.ntnu.no/~mlh/algdat/latitudinary Spørsmål? algdat@idi.ntnu.no Sjekkliste Dette

Detaljer

Hva er en kø? En lineær datastruktur der vi til enhver tid kun har tilgang til elementet som ble lagt inn først

Hva er en kø? En lineær datastruktur der vi til enhver tid kun har tilgang til elementet som ble lagt inn først Køer Hva er en kø? En lineær datastruktur der vi til enhver tid kun har tilgang til elementet som ble lagt inn først Et nytt element legges alltid til sist i køen Skal vi ta ut et element, tar vi alltid

Detaljer

INF Algoritmer og datastrukturer

INF Algoritmer og datastrukturer INF2220 - Algoritmer og datastrukturer HØSTEN 2015 Ingrid Chieh Yu Institutt for informatikk, Universitetet i Oslo Forelesning 4: Prioritetskø og Heap Ingrid Chieh Yu (Ifi, UiO) INF2220 H2015, forelesning

Detaljer

UNIVERSITETET I OSLO

UNIVERSITETET I OSLO Eksamen i UNIVERSITETET I OSLO Det matematisk-naturvitenskapelige fakultet Eksamensdag: 13. desember 2011 Tid for eksamen: 14.30 18.30 Oppgavesettet er på 7 sider. Vedlegg: INF2220 lgoritmer og datastrukturer

Detaljer

Divide-and-Conquer. Lars Vidar Magnusson 13.1.2015

Divide-and-Conquer. Lars Vidar Magnusson 13.1.2015 Divide-and-Conquer Lars Vidar Magnusson 13.1.2015 Kapittel 4 Maximum sub-array problemet Matrix multiplikasjon Analyse av divide-and-conquer algoritmer ved hjelp av substitusjonsmetoden Divide-and-Conquer

Detaljer

INF Algoritmer og datastrukturer

INF Algoritmer og datastrukturer INF2220 - Algoritmer og datastrukturer HØSTEN 2015 Ingrid Chieh Yu Institutt for informatikk, Universitetet i Oslo Forelesning 4: Prioritetskø og Heap Ingrid Chieh Yu (Ifi, UiO) INF2220 H2015, forelesning

Detaljer

TDT4105 Informasjonsteknologi, grunnkurs

TDT4105 Informasjonsteknologi, grunnkurs 1 TDT4105 Informasjonsteknologi, grunnkurs Matlab: Sortering og søking Anders Christensen (anders@idi.ntnu.no) Rune Sætre (satre@idi.ntnu.no) TDT4105 IT Grunnkurs 2 Pensum Matlab-boka: 12.3 og 12.5 Stoffet

Detaljer

INF1020 Algoritmer og datastrukturer

INF1020 Algoritmer og datastrukturer Dagens plan Hashing Hashtabeller Hash-funksjoner Kollisjonshåndtering Åpen hashing (kap. 5.3) Lukket hashing (kap. 5.4) Rehashing (kap. 5.5) Sortering ut fra en hashing-ide (side 66-68) Bøttesortering

Detaljer

INF Algoritmer og datastrukturer

INF Algoritmer og datastrukturer INF2220 - Algoritmer og datastrukturer HØSTEN 2009 Institutt for informatikk, Universitetet i Oslo INF2220, forelesning 5: Prioritetskø og Heap Bjarne Holen (Ifi, UiO) INF2220 H2009, forelesning 5 1 /

Detaljer

EKSAMENSOPPGAVE. INF-1101 Datastrukturer og algoritmer. Adm.bygget, rom K1.04 og B154 Ingen

EKSAMENSOPPGAVE. INF-1101 Datastrukturer og algoritmer. Adm.bygget, rom K1.04 og B154 Ingen Fakultet for naturvitenskap og teknologi EKSAMENSOPPGAVE Eksamen i: Dato: 15.mai 2018 Klokkeslett: 09:00 13:00 Sted: Tillatte hjelpemidler: Adm.bygget, rom K1.04 og B154 Ingen Type innføringsark (rute/linje):

Detaljer

Øvingsforelesning 3: Splitt og hersk. Daniel Solberg

Øvingsforelesning 3: Splitt og hersk. Daniel Solberg Øvingsforelesning 3: Splitt og hersk Daniel Solberg Plan for dagen Vi går raskt gjennom øving 2 Splitt og hersk Algoritmer: Mergesort Quicksort Binærsøk Rekurrenser, masse rekurrenser 2 Splitt og hersk

Detaljer

Grådige algoritmer. Lars Vidar Magnusson Kapittel 16. Aktivitetvelgingsproblemet Huffmankoder

Grådige algoritmer. Lars Vidar Magnusson Kapittel 16. Aktivitetvelgingsproblemet Huffmankoder Grådige Algoritmer Lars Vidar Magnusson 12.3.2014 Kapittel 16 Grådige algoritmer Aktivitetvelgingsproblemet Huffmankoder Ideen bak Grådige Algoritmer Ideen bak grådige algoritmer er å løse optimaliseringsproblem

Detaljer

Løsningsforslag for eksamen i fag SIF8010 Algoritmer og datastrukturer Lørdag 9. august 2003, kl

Løsningsforslag for eksamen i fag SIF8010 Algoritmer og datastrukturer Lørdag 9. august 2003, kl SIF8010 2003-08-09 Stud.-nr: Antall sider: 1 Løsningsforslag for eksamen i fag SIF8010 Algoritmer og datastrukturer Lørdag 9. august 2003, kl. 0900 1500 Faglig kontakt under eksamen: Arne Halaas, tlf.

Detaljer

LO118D Forelesning 2 (DM)

LO118D Forelesning 2 (DM) LO118D Forelesning 2 (DM) Kjøretidsanalyse, matematisk induksjon, rekursjon 22.08.2007 1 Kjøretidsanalyse 2 Matematisk induksjon 3 Rekursjon Kjøretidsanalyse Eksempel Finne antall kombinasjoner med minst

Detaljer

INF1010 notat: Binærsøking og quicksort

INF1010 notat: Binærsøking og quicksort INF1010 notat: Binærsøking og quicksort Ragnhild Kobro Runde Februar 2004 I dette notatet skal vi ta for oss ytterligere to eksempler der rekursjon har en naturlig anvendelse, nemlig binærsøking og quicksort.

Detaljer

Eksamensoppgave i TDT4120 Algoritmer og datastrukturer

Eksamensoppgave i TDT4120 Algoritmer og datastrukturer Eksamensoppgave i TDT4120 Algoritmer og datastrukturer Faglig kontakt under eksamen Magnus Lie Hetland Tlf. 91851949 Eksamensdato 11. august 2014 Eksamenstid (fra til) 0900 1300 Hjelpemiddelkode D. Ingen

Detaljer

INF2220: Forelesning 1. Praktisk informasjon Analyse av algoritmer (kapittel 2) (Binær)trær (kapittel )

INF2220: Forelesning 1. Praktisk informasjon Analyse av algoritmer (kapittel 2) (Binær)trær (kapittel ) INF2220: Forelesning 1 Praktisk informasjon Analyse av algoritmer (kapittel 2) (Binær)trær (kapittel 4.1-4.3 + 4.6) PRAKTISK INFORMASJON 2 Praktisk informasjon Kursansvarlige Ragnhild Kobro Runde (ragnhilk@ifi.uio.no)

Detaljer

Ninety-nine bottles. Femte forelesning. I dagens forelesning: Mest matematiske verktøy. Først: Asymptotisk notasjon. Så: Rekurrensligninger.

Ninety-nine bottles. Femte forelesning. I dagens forelesning: Mest matematiske verktøy. Først: Asymptotisk notasjon. Så: Rekurrensligninger. I dagens forelesning: Mest matematiske verktøy. Først: Asymptotisk notasjon. Så: Rekurrensligninger. Hva slags kjøretid har denne sangen? Hvordan kan du formulere det som en rekurrensligning? Ninety-nine

Detaljer

PG4200 Algoritmer og datastrukturer Forelesning 7

PG4200 Algoritmer og datastrukturer Forelesning 7 PG4200 Algoritmer og datastrukturer Forelesning 7 Lars Sydnes, NITH 19. mars 2014 I. TERMINOLOGI FOR TRÆR TRÆR Lister: Lineære Trær: Hierarkiske Modell / Språk: Bestanddeler: Noder, forbindelser. Forbindelse

Detaljer

Grunnleggende Grafteori

Grunnleggende Grafteori Grunnleggende Grafteori 2. September, 2019 Institutt for Informatikk 1 Dagens plan Terminologi og definisjoner Hvordan representere grafer i datamaskinen Traversering Dybde-først-søk Bredde-først-søk Topologisk

Detaljer

Dijkstras algoritme. Her finnes det også (minst) en riktig rekkefølge for Relax, men den må vi oppdage litt etter hvert.

Dijkstras algoritme. Her finnes det også (minst) en riktig rekkefølge for Relax, men den må vi oppdage litt etter hvert. Her finnes det også (minst) en riktig rekkefølge for Relax, men den må vi oppdage litt etter hvert. Tenk vann som sprer seg i rør: Vi behandler krysningspunktene i den rekkefølgen de fylles. Det må gi

Detaljer

INF2220: Forelesning 2

INF2220: Forelesning 2 INF2220: Forelesning 2 Balanserte søketrær Rød-svarte trær (kapittel12.2) B-trær (kapittel 4.7) REPETISJON: BINÆRE SØKETRÆR 2 Binære søketrær 8 4 12 2 7 9 15 6 11 13 16 For enhver node i et binært søketre

Detaljer

Eksamensoppgave i TDT4120 Algoritmer og datastrukturer

Eksamensoppgave i TDT4120 Algoritmer og datastrukturer Institutt for datateknikk og informasjonsvitenskap Eksamensoppgave i TDT4120 Algoritmer og datastrukturer Faglig kontakt under eksamen Magnus Lie Hetland Telefon 918 51 949 Eksamensdato 4. desember, 2017

Detaljer

INF2220: Forelesning 2. Balanserte søketrær Rød-svarte trær (kapittel12.2) B-trær (kapittel 4.7)

INF2220: Forelesning 2. Balanserte søketrær Rød-svarte trær (kapittel12.2) B-trær (kapittel 4.7) INF2220: Forelesning 2 Balanserte søketrær Rød-svarte trær (kapittel12.2) B-trær (kapittel 4.7) REPETISJON: BINÆRE SØKETRÆR 2 Binære søketrær 8 4 12 2 7 9 15 6 11 13 16 For enhver node i et binært søketre

Detaljer

INF Algoritmer og datastrukturer

INF Algoritmer og datastrukturer INF2220 - Algoritmer og datastrukturer Institutt for informatikk, Universitetet i Oslo INF2220, forelesning 11: Huffman-koding & Dynamisk programmering (Ifi, UiO) INF2220 H2015, forelesning 11 1 / 32 Dagens

Detaljer

Eksamensoppgave i TDT4120 Algoritmer og datastrukturer

Eksamensoppgave i TDT4120 Algoritmer og datastrukturer Institutt for datateknikk og informasjonsvitenskap Eksamensoppgave i TDT0 Algoritmer og datastrukturer Faglig kontakt under eksamen Magnus Lie Hetland Telefon 98 5 99 Eksamensdato 9. august, 07 Eksamenstid

Detaljer

INF Algoritmer og datastrukturer

INF Algoritmer og datastrukturer INF2220 - Algoritmer og datastrukturer HØSTEN 2009 Institutt for informatikk, Universitetet i Oslo INF2220, forelesning 13: Eksamensgjennomgang Bjarne Holen (Ifi, UiO) INF2220 H2009, forelesning 13 1 /

Detaljer

Eksamensoppgave i TDT4120 Algoritmer og datastrukturer

Eksamensoppgave i TDT4120 Algoritmer og datastrukturer Institutt for datateknikk og informasjonsvitenskap Eksamensoppgave i TDT0 Algoritmer og datastrukturer Faglig kontakt under eksamen Magnus Lie Hetland Telefon 98 5 99 Eksamensdato 9. august, 07 Eksamenstid

Detaljer

Logaritmiske sorteringsalgoritmer

Logaritmiske sorteringsalgoritmer Logaritmiske sorteringsalgoritmer Logaritmisk sortering Rekursive og splitt og hersk metoder: Deler verdiene i arrayen i to (helst) omtrent like store deler i henhold til et eller annet delingskriterium

Detaljer