Кратчайший путь в ациклическом графе — различия между версиями
IRomchig (обсуждение | вклад) |
IRomchig (обсуждение | вклад) |
||
Строка 8: | Строка 8: | ||
==Реализация== | ==Реализация== | ||
− | Реализуем данный алгоритм: | + | Реализуем данный алгоритм следующим образом: рассмотрим вершину i. Будем пересчитывать d для всех вершин, выходящих из i: |
//w - матрицы как в описании, d - массив как в описании, p - массив индексов вершин графа в порядке топологической сортировки, i, j - счетчики <br /> | //w - матрицы как в описании, d - массив как в описании, p - массив индексов вершин графа в порядке топологической сортировки, i, j - счетчики <br /> | ||
inputData() //считывание данных <br /> | inputData() //считывание данных <br /> | ||
Строка 27: | Строка 27: | ||
| || '''1''' || '''2''' || '''3''' || '''4''' || '''5''' || '''6''' || '''7''' || '''8''' | | || '''1''' || '''2''' || '''3''' || '''4''' || '''5''' || '''6''' || '''7''' || '''8''' | ||
|- | |- | ||
− | | '''1''' || | + | | '''1''' || - || - || - || 5 || - || - || - || - |
|- | |- | ||
− | | '''2''' || 1 || | + | | '''2''' || 1 || - || 1 || - || 4 || 3 || - || - |
|- | |- | ||
− | | '''3''' || - || - || | + | | '''3''' || - || - || - || - || - || 1 || - || - |
|- | |- | ||
− | | '''4''' || - || - || - || | + | | '''4''' || - || - || - || - || - || - || - || - |
|- | |- | ||
− | | '''5''' || - || - || - || 3 || | + | | '''5''' || - || - || - || 3 || - || - || - || 1 |
|- | |- | ||
− | | '''6''' || - || - || - || 5 || - || | + | | '''6''' || - || - || - || 5 || - || - || 2 || - |
|- | |- | ||
− | | '''7''' || - || - || - || 2 || - || - || | + | | '''7''' || - || - || - || 2 || - || - || - || - |
|- | |- | ||
− | | '''8''' || - || - || - || 1 || - || - || - || | + | | '''8''' || - || - || - || 1 || - || - || - || - |
|} | |} | ||
Требуется найти путь из '''2''' в '''4'''. <br /> | Требуется найти путь из '''2''' в '''4'''. <br /> | ||
Строка 63: | Строка 63: | ||
==Источники== | ==Источники== | ||
*[http://www.ics.uci.edu/~eppstein/161/960208.html Алгоритмы поиска кратчайшего пути в графе] | *[http://www.ics.uci.edu/~eppstein/161/960208.html Алгоритмы поиска кратчайшего пути в графе] | ||
− | *[ | + | *[[Динамическое_программирование#.D0.9F.D1.80.D0.B8.D0.BD.D1.86.D0.B8.D0.BF_.D0.BE.D0.BF.D1.82.D0.B8.D0.BC.D0.B0.D0.BB.D1.8C.D0.BD.D0.BE.D1.81.D1.82.D0.B8_.D0.BD.D0.B0_.D0.BF.D1.80.D0.B5.D1.84.D0.B8.D0.BA.D1.81.D0.B5|Принцип оптимальности на префиксе]] |
* [http://en.wikipedia.org/wiki/Optimal_substructure Принцип оптимальности на подзадаче (в качестве примера разбирается задача поиска кратчайшего пути в ациклическом графе)(англ.)] | * [http://en.wikipedia.org/wiki/Optimal_substructure Принцип оптимальности на подзадаче (в качестве примера разбирается задача поиска кратчайшего пути в ациклическом графе)(англ.)] | ||
[[Категория: Динамическое программирование]] [[Категория: Дискретная математика и алгоритмы]] | [[Категория: Динамическое программирование]] [[Категория: Дискретная математика и алгоритмы]] |
Версия 08:45, 16 января 2012
Пусть дан ациклический ориентированный взвешенный граф. Требуется найти вес кратчайшего пути из u в v
Определение: |
Кратчайший путь из u в v – это такой путь из u в v, что его сумарный вес входящих в него ребер минимален |
Содержание
Решение
Пусть d — массив, где d[i] — вес кратчайшего пути из u в i. Изначально значения d равны бесконечности, кроме d[u], который равен 0. Пусть w[i][j] - вес ребра из i в j. Будем обходить граф в порядке топологической сортировки. Получаем следующие соотношения:
Так как мы обходим граф в порядке топологической сортировки, то на i-ом шаге во всех d[j] (j такие, что: существует ребро из j в i) уже записаны оптимальные ответы, и следовательно в d[i] также будет записан оптимальный ответ.
Реализация
Реализуем данный алгоритм следующим образом: рассмотрим вершину i. Будем пересчитывать d для всех вершин, выходящих из i:
//w - матрицы как в описании, d - массив как в описании, p - массив индексов вершин графа в порядке топологической сортировки, i, j - счетчики
inputData() //считывание данных
for i = 1 to n d[i] = infinity
p = topSort(w) //топологическая сортировка графа
d[p[u]] = 0
for i = 1 to n for j: есть ребро из p[i] в j d[j] = min(d[j], d[p[i]] + w[p[i]][j])
writeData(); // запись данных
Пример
Пусть дан граф со следующими весами w ребер:
1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | |
1 | - | - | - | 5 | - | - | - | - |
2 | 1 | - | 1 | - | 4 | 3 | - | - |
3 | - | - | - | - | - | 1 | - | - |
4 | - | - | - | - | - | - | - | - |
5 | - | - | - | 3 | - | - | - | 1 |
6 | - | - | - | 5 | - | - | 2 | - |
7 | - | - | - | 2 | - | - | - | - |
8 | - | - | - | 1 | - | - | - | - |
Требуется найти путь из 2 в 4.
Массив p будет выглядеть следующим образом:
1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 |
2 | 3 | 6 | 7 | 1 | 5 | 8 | 4 |
Массив d будет выглядеть следующим образом:
1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 |
1 | 0 | 3 | 5 | 3 | 2 | 4 | 4 |
Ответ равен 2.