E. W. Dijkstra Plus court chemin Algorithme de Dijkstra Plus courts chemins dans un graphe F. Guinand, S. Balev Master I - Le Havre F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra Plan 1 E. W. Dijkstra 2 Plus court chemin 3 Algorithme de Dijkstra F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra Le plus court chemin d’un graphe n’est jamais celui que l’on croit, il peut surgir de nulle part, et la plupart du temps il n’existe pas E. W. Dijkstra F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra Edsger Wybe Dijkstra (1930 - 2002) F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra E.W. Dijkstra mathématicien et informaticien début en physique théorique contributions majeures en informatique notion de sémaphore, section critique, dîner des philosophes programmation structurée → sus au goto contributeur de Algol W, Algol. théorie des graphes (1950s, 60s) =⇒ prix Turing en 1972 notion d’autostabilisation en informatique répartie (1974) F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra L’informatique n’est pas plus la science des ordinateurs que l’astronomie n’est celle des télescopes F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra Tester un programme peut démontrer la présence de bugs, jamais leur absence F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra La programmation par objets est une idée exceptionnellement mauvaise qui ne pouvait naître qu’en Californie F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra Pourquoi s’intéresse t-on à ces problèmes ? 1 postier chinois et plus généralement problèmes de tournées 2 ordonnancement 3 routage 4 programmation dynamique 5 labyrinthe 6 investissements/gestion de stocks F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra Types de problèmes le problème de la détermination d’un plus court chemin entre deux sommets, le problème de la détermination des plus courts chemin d’un sommet vers l’ensemble des autres sommets du graphe, le calcul du plus court chemin pour l’ensemble des couples de sommets du graphe. F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra Contraintes si les longueurs sont toutes positives ou nulles si les longueurs sont toutes égales à l’unité si le graphe et les longueurs sont quelconques si le graphe est sans circuit si le graphe est connexe ou fortement connexe (graphe orienté) F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra algorithme de Dijkstra algorithme de Bellman-Ford algorithme de Floyd-Warshall F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra Problème Dans un graphe orienté G(V , A), trouver les plus courts chemins à partir d’un sommet de départ s ∈ V vers tous les autres sommets. F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra Principe On maintient T - ensemble de sommets traités d(v ), v ∈ V - longueur du plus court chemin de s à v qui ne passe que par des sommets de T À chaque itération on choisit le sommet non-traité le plus proche de T on l’ajoute à T on met à jour les d de ses voisins F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra Algorithme – version simple T ←∅ Pour v ∈ V Faire d(v ) ← ∞ finPour d(s) ← 0 TantQue (T 6= V ) v ← argmin{d(u) : u 6∈ T } T ← T ∪ {v } Pour u ∈ voisins(v ) Faire d(u) ← min{d(u), d(v ) + wvu } finPour finTantQue F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra Exemple a 4 7 b 5 c 1 1 4 1 d 2 e g f 2 5 1 1 h 2 i 4 j Trouver les plus courts chemins de c vers tous les autres sommets F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra Question On a les longueurs des chemins, mais comment obtenir les chemins eux-mêmes ? F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra Maintien des chemins T ←∅ Pour v ∈ V Faire d(v ) ← ∞ finPour d(s) ← 0 pred(s) ← null TantQue (T 6= V ) v ← argmin{d(u) : u 6∈ T } T ← T ∪ {v } Pour u ∈ voisins(v ) Faire Si (d(u) > d(v ) + wvu ) Alors d(u) ← d(v ) + wvu pred(u) ← v finSi finPour finTantQue F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra Terminaison et correction Démonstration par récurrence sur la taille de T avec les hypothèses suivantes : Pour v ∈ T , d(v ) est la longueur du plus court chemin de s àv Pour v 6∈ T , d(v ) est la longueur du plus court chemin ne passant que par sommets de T pour arriver en v F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra Complexité Implémentation naïve : O(n2 ) n itérations de la boucle TantQue recherche du sommet avec d minimum : O(n) On peut réduire la complexité en utilisant des structures de données performantes F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra File prioritaire Une structure de données permettant de stocker des éléments triés (partiellement) en fonction de leur « priorité » et d’extraire rapidement l’élément de priorité minimum. Opérations : F.estVide() : permet de vérifier si la fille est vide F.extraireMin() : permet de récupérer l’élément de priorité minimum F.ajouter(e, p) : permet d’ajouter l’élément e de priorité p. Si e est déjà dans F, change sa priorité. F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra Algorithme – avec file de priorité Pour v ∈ V Faire d(v ) ← ∞ finPour d(s) ← 0 F.initialiser() F.ajouter(s, 0) TantQue (non F.estVide()) v ← F.extraireMin() Pour u ∈ voisins(v ) Faire Si (d(u) > d(v ) + wvu ) Alors d(u) ← d(v ) + wvu F.ajouter(u, d(u)) finSi finPour finTantQue F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra File prioritaire – implémentation avec listes Liste non-trié F.estVide() : O(1) F.extraireMin() : O(n) F.ajouter(e, p) : O(1) Liste trié F.estVide() : O(1) F.extraireMin() : O(1) F.ajouter(e, p) : O(n) Dans les deux cas, la complexité de l’algorithme de Dijkstra reste O(n2 ) F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra File prioritaire – implémentation performante Heureusement, il existe des structures de données, telles que les tas ou les arbres binaires de recherche équilibrés permettant de rendre performantes les deux opérations : F.estVide() : O(1) F.extraireMin() : O(log n) F.ajouter(e, p) : O(log n) Avec ce type de structures, la complexité de l’algorithme de Dijkstra passe à O(m + n log n) F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra Complexité – récapitulation Impléméntation naïve : O(n2 ) Implémentation efficace : O(m + n log n) Exemple. Soit n = 1000 et m = 10000 Impléméntation naïve : ≈ 1 000 000 opérations Implémentation efficace : ≈ 20 000 Accélération : ≈ ×50 F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra Exercice Démontrer que l’algorithme de Dijkstra effectue un parcours dans le graphe Rappel. Un parcours d’un graphe à partir d’un sommet s est la génération d’une liste L de sommets, telle que : L contient tous les sommets de G atteignables à partir de s; s est le premier élément de L ; chaque sommet de G est au plus une fois dans L ; pour chaque sommet v 6= s dans L il existe un voisin de v avant lui dans L F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra Limitations L’algorithme de Dijkstra ne s’applique que pour des graphes dont le poids des arêtes/arcs est positif ou nul. F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra Exemple pour lequel Dijkstra ne s’applique pas a −2 1 2 c b d −5 4 2 5 e f Trouver les plus courts chemins de a vers tous les autres sommets F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra Le cas de poids négatifs Comment adapter l’algorithme de Dijkstra pour le cas de poids négatifs ? Procedure maj((u, v ) ∈ E) d(v ) = min{d(v ), d(u) + wuv } FinProcedure Donne la valeur correcte de d(v ) si u et le sommet avant v dans le plus court chemin de s à v et si la valeur de d(u) est correcte Quel que soit le nombre d’appels, d(v ) reste une borne supérieure sur la distance entre s et v F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra Le cas de poids négatifs Considérons le plus court chemin entre s et v : s − u1 − u2 − · · · − uk − v Si la séquence des mises à jour inclut (s, u1 ), (u1 , u2 ), . . . (uk , v ) dans cet ordre (mais pas forcement consécutivement), la distance de s à v sera correctement calculée. Mais comment savoir le bon ordre ? → Mettre à jour tous les arcs n − 1 fois. F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra Algorithme de Bellman-Ford Pour v ∈ V Faire d(v ) ← ∞ finPour d(s) ← 0 Répéter n − 1 fois Pour e ∈ E faire maj(e) finPour finRépéter Amélioration possible : s’arrêter si pendant une itération il n’y a pas eu de mise à jour. F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra Exercices Correction et complexité de l’algorithme de Bellman-Ford Le problème du plus court chemin est mal posé dans le cas de circuits négatifs. Néanmoins, on peut modifier l’algorithme de Bellman-Ford pour détecter ces circuits. Comment ? F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra Le plus court chemin entre toutes les paires de sommets Principe : d(i, j, k ) - la longueur du plus court chemin entre i et j en utilisant des sommets intermédiaires seulement parmi {1, . . . , k } Au début d(i, j, 0) = wij si (i, j) ∈ E et ∞ sinon On ajoute un sommet k à chaque itération en mettant à jour tous les d(i, j, k ) F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra Algorithme de Floyd-Warshall Pour i de 1 à n Faire Pour j de 1 à n Faire d(i, j) = wij ou ∞ finPour finPour Pour k de 1 à n Faire Pour i de 1 à n Faire Pour j de 1 à n Faire d(i, j) = min{d(i, j), d(i, k ) + d(k , j)} finPour finPour finPour F. Guinand, S. Balev Plus courts chemins dans un graphe E. W. Dijkstra Plus court chemin Algorithme de Dijkstra Exercices Correction et complexité de l’algorithme de Floyd-Warshall Détection de cycles négatifs ? F. Guinand, S. Balev Plus courts chemins dans un graphe