Grafer
Anvendelser av grafer Passer for modeller/datastrukturer med usystematiske forbindelser Ikke-lineære og ikke-hierarkiske koblinger mellom dataobjektene Modellering av nettverk: Veisystemer/rutekart Kjemiske prosesser Sosiale forhold (vennestrukturer på acebook) Organisasjonsmodeller Internett/ LAN
lyruter
Veikart med avstandsangivelse
Molekylmodell
Nettverk for signalbehandling
Venner på acebook
Grafer: Definisjon En graf G består av en mengde V med noder (vertices) sammen med en mengde E med kanter (edges), G = (V, E) En kant er et par (v, w) av noder, som angir at det er en forbindelse mellom nodene v og w er naboer i G Grafen er rettet hvis kantene er ordnede par (ikke toveisforbindelser) ellers er den urettet Grafen er vektet hvis det er en vekt/ kostnad/ avstand forbundet med kantene ( kostnaden ved å gå fra en node til en annen)
Urettede grafer Kantene i grafen har ikke retning (er toveis) En vei i grafen er en sekvens av noder der hver node er nabo til neste node i sekvensen En cykel er en vei med minst 3 noder, der siste node på veien er nabo med første En urettet graf er sammenhengende hvis det finnes en vei fra enhver node i grafen til enhver annen node, ellers er den usammenhengende En urettet graf er et tre hvis den er sammenhengende og uten cykler
Sammenhengende, urettet graf Noder: 0, 1, 2, 3, 4, 5, 6 Kanter: (0, 1), (1, 2), (1, 3), (2, 3), (2, 4), (4, 6), (5, 6) Vei: 0, 1, 2, 4, 6, 5 Cykel: 1, 3, 2
Usammenhengende, urettet graf Urettet graf som også er et tre
Rettede grafer Kantene i grafen har en retning (ikke toveis): Må ha to kanter for å ha forbindelse begge veier mellom to noder Veiene i grafen er rettede (har en retning) En rettet graf er sterkt sammenhengende hvis det finnes en rettet vei fra enhver node til enhver annen node i grafen En rettet graf er svakt sammenhengende hvis det finnes en vei fra enhver node til enhver annen node i den tilsvarende urettede grafen
Svakt sammenhengende rettet graf
Sterkt sammenhengede rettet graf
Vektede grafer Hver kant har en lengde (eller kostnad) En kant består av tre deler: o noder En verdi/kantlengde En vektet graf kan være rettet eller urettet Veiene i grafen har en vektet veilengde*: Summen av lengdene av alle kantene langs veien Vektede grafer kalles også nettverk *: Uvektet veilengde er antall kanter langs veien
Urettet vektet graf
Rettet vektet graf
Antall kanter i en graf med n noder Kan oftest anta at det aldri er mer enn én kant fra en node til enhver annen node i grafen Maksimalt antall kanter er da n2 Grafer og nettverk er oftest tynt befolket, dvs, at antall kanter er mye mindre enn n2, vanligvis O(n) Sparse graph: Antall kanter er O(n) Dense graph: Antall kanter er O(n2) Viktig at implementasjon/lagring av grafer og grafalgoritmer er effektive når grafen er sparse
3-D dense graph
Implementasjon/lagring av grafer renger å lagre: Dataene i hver node Hvilke noder som er naboer i grafen (kantene) Evt. lengde/kostnad for hver kant for vektet graf Vanlig å lagre urettede grafer og rettede grafer på samme måte: En urettet kant (v, w)* lagres som de to rettede kantene (v, w) og (w, v) o standard måter å lagre grafen på: Nabomatrise Nabolister * VW?
Nabomatriser (adjacency matrices) Anta at de n nodene i en uvektet graf er nummerert fra 0 til n 1 Hele grafen kan da representeres med en todimensjonal boolsk n x n tabell/matrise G der: G[i][j] er true hvis og bare hvis det går en kant fra node i til node j, og false ellers or urettede grafer blir nabomatrisen symmetrisk om hoveddiagonalen, G[i][j] = G[j][i] (redundans) or vektede grafer kan det brukes en matrise med kantlengder (heltall/reelle tall), der: G[i][j] er lik kantlengden hvis det går en kant fra node i til node j, og lik (f.eks.) ellers
Nabomatrise for urettet graf 0 1 2 3 4 5 6 0 1 2 3 4 5 6
Nabomatrise for rettet graf 1 2 3 4 5 6 1 2 3 4 5 6
Nabo-/kantmatrise for vektet graf 0 1 2 3 4 5 6 0 0 2 1 1 0 3 10 2 4 0 5 3 2 0 2 8 4 4 0 6 5 0 6 1 0
Nabolister (adjacency lists/edge lists) Nabomatriser bruker O(n2) hukommelse, sløsing med plass siden de fleste grafer er sparse Nabolister: Grafen representeres som en array med lister, én liste for hver node i grafen Listen for en node inneholder nodens direkte naboer i grafen Rettede og urettede grafer kan behandles likt, urettede kanter lagres to ganger Nabolisten for en sparse graf med med n noder krever O(n) hukommelse
Nabolister for en rettet, vektet graf
raversering av (søk i) grafer raversering (søking): Oppsøke alle noder i grafen en og bare en gang Problemer ved graftraversering: Det er oftest ingen rot /naturlig startpunkt i en graf Grafen kan være cyklisk slik at en node oppsøkes flere ganger. Løses ved å merke oppsøkte noder. Grafen kan være usammenhengende/svakt sammenhengede, slik at ikke alle noder kan nås fra en gitt node. Kan løses ved å prøve traverseringer med start én gang fra alle noder i grafen. o standard rekkefølger for traversering av grafer: Dybde-først (Depth-irst Search DS) Bredde først (Breadth-irst Search BS)
Dybde-først søk vs. bredde-først elles for begge traverseringsmetoder: Starter med å oppsøke en node, markeres som oppsøkt Legger alle nodens uoppsøkte naboer inn i en (hjelpe) datastruktur ortsetter med å ta ut første uoppsøkte node fra datastrukturen, og oppsøker denne på samme måte orskjeller: Bredde-først: Lagrer uoppsøkte noder i en (IO) kø. De uoppsøkte nodene nærmest startnoden oppsøkes først. Søkingen brer seg i ringer fra utgangspunktet. Dybde-først: Lagrer uoppsøkte noder på en stack (LIO). Vil gå i dybden langs veier med uoppsøkte noder.
Animasjon av DS og BS
raversering: Eksempel Starter i A, oppsøker naboer fra venstre mot høyre Dybde først: A, D, M, H, N, L, Q, J, P, O, E,, C, B, I, K, G Bredde først: A,, D, C, B, E, M, I, J, H, Q, K, G, P, N, L, O
raversering og spenn-trær* Spenn-tre: Et tre (ikke-cyklisk) som består av alle nodene i en graf og et utvalg av kantene, slik at alle nodene er forbundet med hverandre Læreboka: Algoritme for å finne spenn-treet med minst total veilengde (minimum spanning tree) i en vektet graf (MS-algoritmen, 1957) Kantene som følges i en traversering av en graf, vil alltid utgjøre et spenn-tre Dybde-først: Spenn-treet blir høyt og ubalansert Bredde-først: Lavere, mer balansert spenn-tre * eng.: spanning tree
Spenntrær for DS og BS
Dybde-først søk: Implementasjon Analogt med preorder traversering av trær Implementeres naturlig rekursivt: DS(node x) { } oppsøk(x) for hver node y som er nabo med x Hvis y ikke er oppsøkt DS(y) Se Java-kode med eksempel for denne grafen Læreboka: AD og ikke-rekursiv DS-iterator med stack
Bredde-først søk: Implementasjon Analogt med bredde-først traversering av trær Implementeres iterativt med bruk av en kø: BS(node start) { enqueue(start) så lenge kø ikke tom { x = dequeue() oppsøk(x) for hver node y som er nabo med x hvis y ikke er oppsøkt eller ligger i kø enqueue(y) } } Se Java-kode med eksempel for denne grafen Læreboka: AD med BS-iterator
Nåbarhet (og konnektivitet) Ønsker å finne ut hvilke noder som det finnes veier mellom i grafen (nåbarhet/ reachability) Evt. også om grafen er sammenhengende (konnektivitet/ connectivity) o standardproblemer: inn alle noder som er nåbare fra en bestemt node: Single source reachability problem (SSRP) inn alle noder som kan når fra enhver node i grafen All-pairs reachability problem (APRP)
Single source reachability problem Alle noder nåbare fra 1: 4, 5, 6 Alle noder nåbare fra 2: 1, 3, 4, 5, 6 SSRP løses enkelt ved bare å gjøre et dybdeførst søk fra startnoden
All-pairs reachability problem Alle noder nåbare fra 1: Alle noder nåbare fra 2: Alle noder nåbare fra 3: Alle noder nåbare fra 4: Alle noder nåbare fra 5: Alle noder nåbare fra 6: 4, 5, 6 1, 3, 4, 5, 6 1, 2, 4, 5, 6 1, 6, 5 1, 4, 6 1, 4, 5
Løsningsmatrise: All-pairs reachability problem 1 2 3 4 5 6 1 2 3 4 5 6
3 o O(n ) algoritmer for løsning av APRP Dybde-først søk/traversering n ganger, én gang med start i hver node i grafen: Kan også brukes for å teste konnektivitet: Hvis alle traverseringene er innom alle n noder, er grafen (sterkt) sammenhengende Warshall-algoritmen inner løsningsmatrisen til APRP ved å bygge ut nabomatrisen til grafen med alle mulige veier Prinsipp: Det finnes en vei fra node i til node j, hvis det finnes en vei fra node i til node k, og fra node k til node j Se Java-kode for løsning av APRP med begge metoder, anvendt på denne grafen
Korteste-vei problemer Algoritmer for vektede grafer* o standardproblemer (som for nåbarhet); inn korteste vei fra én bestemt node til alle andre noder i grafen: Single source shortest path problem inn korteste vei fra alle noder til alle andre noder i grafen: All-pairs shortest path problem Varianter av korteste-vei problemer (ravelling Salesman's Problem, flåtestyring, ruteplanlegging, optimaliseringer) forekommer mye i praksis *: or uvektede grafer finnes korteste veier enkelt med bredde-først søk
Vektede grafer og korteste-vei problemer Representerer grafen som en nabomatrise med kantlengder Hvis det ikke går en kant mellom to noder, legger vi inn en uendelig stor kantlengde 0 1 2 3 4 5 6 0 0 2 1 v 1 0 3 10 2 4 0 5 3 2 0 2 8 4 4 0 6 5 0 6 1 0
All-pairs shortest path problem Kan løses med loyd's algoritme (R. loyd, 1962) En variant av Warshall-algoritmen: ar utgangspunkt i nabo-/kantlengdematrisen Bygger ut alle mulige veier i grafen inne i matrisen, tar hele tiden vare på den korteste veien som til nå er funnet mellom to noder Er O(n3) Se Java-kode med løsning for denne grafen
Single source shortest path problem Kan løses med Dijkstras algoritme (E.W. Dijkstra, 1959): Standard algoritme i svært mange systemer, f.eks. GPSenheter og Google Maps Bruker n steg. I hvert steg finnes korteste vei fra startnoden til én ny node, Bruker to hjelpearrayer: En boolsk array funnet av lengde n, med alle elementer lik false til å begynne med, for å merke av nodene som vi allerede har funnet korteste vei til En array avstand som lagrer den hittil korteste veien som vi til nå har sett, fra startnoden til alle andre noder i grafen. Alle elementer er lik uendelig til å begynne med, unntatt for startnoden der korteste vei settes lik 0. Løsningen ligger i arrayen avstand når algoritmen er ferdig.
Dijkstras algoritme: Eksempel
Dijkstras algoritme: Animasjon Merk: Kantene i figuren er tegnet like lange som vekten/kantlengden
Dijkstras korteste-vei algoritme med start i S 1. Sett avstand lik 0 for S, og lik for alle de andre n 1 nodene 2. Sett ferdig lik false for alle noder i grafen. Sett startnoden S som current. Sett antall_funnet lik 0. 3. or alle naboer i til noden som er current, og som har ferdig[i] lik false: 3.1 La length være lengden av kanten fra current til node i 3.2 Hvis avstand[current] + length < avstand[i]: 3.2.1 avstand[i] = avstand[current] + length 4. Sett ferdig[current] lik true. Øk antall_funnet med 1. 5. Hvis antall_funnet er lik n, er algoritmen ferdig 6. Sett current lik den av nodene som har minst verdi av avstand og som også har ferdig lik false. Gå til steg 3.
Dijkstra: Effektivitet og implementasjon 2 Er O(n ) i originalutgaven Blir O(n log n) med smart koding; Bruker en minheap til å lagre avstandene, for raskt å kunne lagre og finne noden med minst veilengde Dijkstra kan også brukes til å løse all-pairs shortest path problemet, ved å starte algoritmen én gang fra hver node i grafen Se Java-kode med løsning for denne grafen