Algorytm Yena

Algorytm Yena oblicza z jednego źródła K - najkrótsze ścieżki bez pętli dla grafu z nieujemnym kosztem krawędzi . Algorytm został opublikowany przez Jin Y. Yen w 1971 roku i wykorzystuje dowolny algorytm najkrótszej ścieżki , aby znaleźć najlepszą ścieżkę, a następnie przechodzi do znalezienia K - 1 odchyleń najlepszej ścieżki.

Algorytm

Terminologia i notacja

Notacja Opis
Rozmiar wykresu, czyli liczba węzłów w sieci.
Ja wykresu, gdzie się od N . to, że wykresu i węzłem
Koszt przewagi między i jot ) .
K { najkrótsza ścieżka od do się od do . Wtedy , gdzie jest drugim węzłem i jest trzecim węzłem najkrótsza ścieżka i tak dalej.
Ścieżka odchylenia od w węźle gdzie się od do . Zauważ że maksymalna wartość to , która jest węzłem tuż przed zlewem w . najkrótsza droga. że ścieżka odchylenia nie może odbiegać od ścieżki w zlewie Ścieżki i samą _ krawędź różni się od dowolnej ścieżki w gdzie waha się od k .
Ścieżka główna , która wynika z tego, że aż do węzeł ZA .
Ścieżka ostrogi , która zaczyna w węzła ZA i kończy się przy zlewie.

Opis

Algorytm można podzielić na dwie części, określając pierwszą najkrótszą ścieżkę , a następnie wszystkie inne k - najkrótsze ścieżki . Zakłada się, że pojemnik zawierał - ścieżkę, podczas gdy pojemnik będzie zawierał potencjalne k - ścieżki. Aby określić _ od źródła do ujścia można zastosować dowolny efektywny algorytm najkrótszej ścieżki .

znaleźć gdzie się , że ​​wszystkie ścieżki z k do zostały znalezione wcześniej. Iterację można podzielić na dwa procesy, znajdując i wybierając ścieżkę o minimalnej długości, aby stać się . w tej iteracji od displaystyle do

Pierwszy proces można dalej podzielić na trzy operacje, wybierając , znajdując , a następnie dodanie do kontenera . Ścieżka główna znalezienie ścieżki podrzędnej w który następuje po pierwszych węzłach gdzie się od k . , ścieżka koszt Dalej ścieżka ostrogi, , znajduje się przez obliczenie najkrótszej ścieżki od węzła ostrogi, do zlewu. Usunięcie wcześniej używanych krawędzi z do , że ​​ścieżka ostrogi jest inna. ostrogi , dodaje się do . Następnie krawędzie, które zostały usunięte, czyli których koszt był ustawiony na nieskończoność, są przywracane do wartości początkowych.

Drugi proces określa odpowiednią ścieżkę dla, kontenerze koszcie. algorytm do iteracji.

Pseudo kod

Algorytm zakłada, że ​​algorytm Dijkstry służy do znalezienia najkrótszej ścieżki między dwoma węzłami, ale w jego miejsce można zastosować dowolny algorytm najkrótszej ścieżki.

         0  function  YenKSP(Graph, source, sink, K):  // Określ najkrótszą ścieżkę od źródła do ujścia.  A[0] = Dijkstra(wykres, źródło, ujście);  // Zainicjuj zestaw do przechowywania potencjalnej k-tej najkrótszej ścieżki.  B = [];  for  k  od  1  do  K:  // Węzeł ostrogi rozciąga się od pierwszego węzła do przedostatniego węzła w poprzedniej k-najkrótszej ścieżce.  dla  i  od  do  size(A[k − 1]) − 2:  // Węzeł Spur jest pobierany z poprzedniej k-najkrótszej ścieżki, k − 1.  spurNode = A[k-1].node(i);  // Sekwencja węzłów od źródła do węzła ostrogi poprzedniej k-najkrótszej ścieżki.  rootPath = A[k-1].nodes(0, i);  dla każdej  ścieżki p  w  A:  if  rootPath == p.nodes(0, i):  // Usuń łącza, które są częścią poprzednich najkrótszych ścieżek, które mają tę samą ścieżkę główną.  usuń p.edge(i,i + 1)  z 
            
             Wykres;  dla każdego  węzła rootPathNode  w  rootPath z wyjątkiem spurNode: usuń rootPathNode  z  Graph;  // Oblicz ścieżkę ostrogi od węzła ostrogi do ujścia.  // Rozważ także sprawdzenie, czy znaleziono ścieżkę spurPath  ostroPath = Dijkstra(Graph, spurNode, sink);  // Cała ścieżka składa się ze ścieżki głównej i ścieżki ostrogi.  totalPath = rootPath + spurPath;  // Dodaj potencjalną k-najkrótszą ścieżkę do sterty.  Jeśli 
            
             (totalPath nie w B): B.append(totalPath);  // Dodaj z powrotem krawędzie i węzły, które zostały usunięte z grafu.  przywróć krawędzie  do  wykresu; przywróć węzły w rootPath   do  Graph;  if  B jest puste:  // Obsługuje to przypadek, gdy nie ma ścieżek ostrogowych lub nie ma już ścieżek ostrogowych.  // Może się to zdarzyć, jeśli ścieżki ostrogowe zostały już wyczerpane (dodane do A),  // lub w ogóle nie ma ścieżek ostrogowych - na przykład gdy zarówno wierzchołki źródłowe, jak i ujścia 
             // leżeć w „ślepym zaułku”.  przerwa;  // Sortowanie potencjalnych k-najkrótszych ścieżek według kosztu.  sortowanie B.();  // Dodanie ścieżki o najniższym koszcie staje się k-najkrótszą ścieżką.  A[k] = B[0];  // Właściwie powinniśmy raczej użyć przesunięcia, ponieważ usuwamy pierwszy element  B.pop();  powrót  A; 

Przykład

Yen's k-shortest path algorithm, K = 3, A to F

K - najkrótszej ścieżki jena do obliczenia trzech ścieżek od do . Algorytm Dijkstry służy do obliczenia najlepszej ścieżki od do , czyli z kosztem 5. Ta ścieżka jest dołączana do kontenera staje się pierwszą k - ścieżką, .

Węzeł do staje się węzłem bocznym z własną ścieżką korzeniową, . Krawędź ścieżką główną Algorytm Dijkstry służy do obliczenia ścieżki ostrogi ( , z kosztem 8. jest dodawane do pojemnika potencjalna k - ścieżka.

Węzeł staje się węzłem bocznym z - . Krawędź ponieważ pokrywa się główną Algorytm Dijkstry służy do obliczania ścieżki ostrogi ( , z kosztem 7. jest dodawane do kontenera potencjalna k - ścieżka.

Węzeł węzłem bocznym ze ścieżką główną, do . Krawędź jest usuwana, ponieważ pokrywa się ze ścieżką główną i ścieżką w kontenerze ( . Algorytm Dijkstry służy do obliczania ścieżki ostrogi sol , z kosztem 8. jest dodawane do pojemnika potencjalna k - ścieżka.

trzech ścieżek w kontenerze B, wybrano, aby stać się najniższy koszt 7. Proces ten jest kontynuowany do trzeciej k - najkrótszej ścieżki. Należy jednak zauważyć, że w ramach tej trzeciej iteracji niektóre ścieżki ostrogi nie istnieją. A ścieżka, która została wybrana, to .

Cechy

Złożoność przestrzeni

Aby zapisać krawędzie wykresu, najkrótsza lista najkrótsza lista ścieżek , adresy pamięci są wymagane. W gorszym każdy węzeł na wykresie ma krawędź do każdego innego węzła na wykresie, dlatego są adresy Tylko są potrzebne dla obu list. i najwyżej będą przechowywane tylko może mieć węzły

Złożoność czasowa

Złożoność czasowa algorytmu Yena zależy od algorytmu najkrótszej ścieżki używanego do obliczania ścieżek bocznych, więc przyjmuje się algorytm Dijkstry. Algorytm Dijkstry ma gorszą złożoność czasową przypadku przy użyciu sterty Fibonacciego staje się , gdzie jest liczbą krawędzi na wykresie Ponieważ algorytm Yen sprawia, że wzywa Dijkstrę do obliczania bocznych ścieżek, gdzie bocznych ścieżek. skondensowanym wykresie oczekiwana wartość to najgorszym przypadkiem jest . , złożoność czasowa staje się .

Ulepszenia

Algorytm jena można ulepszyć, używając sterty do przechowywania k - najkrótszych ścieżek. Użycie sterty zamiast listy poprawi wydajność algorytmu, ale nie złożoność. Jedną z metod na nieznaczne zmniejszenie złożoności jest pominięcie węzłów, w których nie istnieją ścieżki ostrogi. Ten przypadek jest tworzony, gdy wszystkie ścieżki ostrogi z węzła ostrogi zostały użyte w poprzednim . Ponadto, K ścieżki o minimalnej długości, w odniesieniu do tych w kontenerze można je wyodrębnić i wstawić do kontenera nie zostaną znalezione krótsze ścieżki.

modyfikacja Lawlera

Eugene Lawler zaproponował modyfikację algorytmu Yena, w której ścieżki duplikatów nie są obliczane, w przeciwieństwie do oryginalnego algorytmu, w którym są one obliczane, a następnie odrzucane, gdy okażą się duplikatami. Te zduplikowane ścieżki wynikają z obliczenia bocznych ścieżek węzłów w korzeniu . Na przykład, węźle odbiega od . Każda ścieżka ostrogi, która jest obliczona, będzie duplikatem, ponieważ gdzie zostały już obliczone podczas iteracji. . Dlatego należy obliczyć tylko ścieżki ostrogi dla ostrogi, gdzie waha się od do . Aby wykonać operację dla , potrzebny jest rekord identyfikujący węzeł, z którego rozgałęził się .

Zobacz też

Linki zewnętrzne