shortestpath

Самый короткий путь между двумя одинарными узлами

Описание

пример

P = shortestpath(G,s,t) вычисляет самый короткий путь, начиная с исходного узла s и заканчивается на целевом узле t. Если график взвешен (то есть G.Edges содержит переменную Weight), затем эти веса используются в качестве расстояний вдоль ребер в графике. В противном случае все расстояния по ребрам будут 1.

пример

P = shortestpath(G,s,t,'Method',algorithm) опционально задает алгоритм, который будет использоваться при вычислении кратчайшего пути. Для примера, если G является взвешенным графиком, тогда shortestpath(G,s,t,'Method','unweighted') игнорирует веса кромок в G и вместо этого рассматривает все веса кромок как 1.

пример

[P,d] = shortestpath(___) дополнительно возвращает длину кратчайшего пути, d, с использованием любого из входных параметров в предыдущих синтаксисах.

пример

[P,d,edgepath] = shortestpath(___) дополнительно возвращает индексы ребер edgepath всех ребер на самом коротком пути из s на t.

Примеры

свернуть все

Создайте и постройте ориентированного графа.

s = [1 1 2 3 3 4 4 6 6 7 8 7 5];
t = [2 3 4 4 5 5 6 1 8 1 3 2 8];
G = digraph(s,t);
plot(G)

Figure contains an axes. The axes contains an object of type graphplot.

Вычислите кратчайший путь между узлами 7 и 8.

P = shortestpath(G,7,8)
P = 1×5

     7     1     3     5     8

Создайте и постройте график с взвешенными ребрами.

s = [1 1 1 2 2 6 6 7 7 3 3 9 9 4 4 11 11 8];
t = [2 3 4 5 6 7 8 5 8 9 10 5 10 11 12 10 12 12];
weights = [10 10 10 10 10 1 1 1 1 1 1 1 1 1 1 1 1 1];
G = graph(s,t,weights);
plot(G,'EdgeLabel',G.Edges.Weight)

Figure contains an axes. The axes contains an object of type graphplot.

Найдите кратчайший путь между узлами 3 и 8 и задайте два выхода, чтобы также вернуть длину пути.

[P,d] = shortestpath(G,3,8)
P = 1×5

     3     9     5     7     8

d = 4

Поскольку края в центре графика имеют большие веса, самый короткий путь между узлами 3 и 8 обходит контур графика, где веса кромок наименьшие. Этот путь имеет общую длину 4.

Создайте и постройте график с взвешенными ребрами, используя пользовательские координаты узла.

s = [1 1 1 1 1 2 2 7 7 9 3 3 1 4 10 8 4 5 6 8];
t = [2 3 4 5 7 6 7 5 9 6 6 10 10 10 11 11 8 8 11 9];
weights = [1 1 1 1 3 3 2 4 1 6 2 8 8 9 3 2 10 12 15 16];
G = graph(s,t,weights);

x = [0 0.5 -0.5 -0.5 0.5 0 1.5 0 2 -1.5 -2];
y = [0 0.5 0.5 -0.5 -0.5 2 0 -2 0 0 0];
p = plot(G,'XData',x,'YData',y,'EdgeLabel',G.Edges.Weight);

Figure contains an axes. The axes contains an object of type graphplot.

Нахождение кратчайшего пути между узлами 6 и 8 на основе весов ребер графика. Выделите этот путь зеленым цветом.

[path1,d] = shortestpath(G,6,8)
path1 = 1×5

     6     3     1     4     8

d = 14
highlight(p,path1,'EdgeColor','g')

Figure contains an axes. The axes contains an object of type graphplot.

Задайте Method как unweighted игнорировать веса кромок, вместо этого обрабатывать все ребра так, как если бы они имели вес 1. Этот метод создает другой путь между узлами, который ранее имел слишком большую длину пути, чтобы быть самым коротким пути. Выделите этот путь красным цветом.

[path2,d] = shortestpath(G,6,8,'Method','unweighted')
path2 = 1×3

     6     9     8

d = 2
highlight(p,path2,'EdgeColor','r')

Figure contains an axes. The axes contains an object of type graphplot.

Постройте график кратчайшего пути между двумя узлами в мультиграфике и выделите определенные ребра, которые проходят.

Создайте взвешенный мультиграфик с пятью узлами. Несколько пар узлов имеют более одного ребра между ними. Постройте график для ссылки.

G = graph([1 1 1 1 1 2 2 3 3 3 4 4],[2 2 2 2 2 3 4 4 5 5 5 2],[2 4 6 8 10 5 3 1 5 6 8 9]);
p = plot(G,'EdgeLabel',G.Edges.Weight);

Figure contains an axes. The axes contains an object of type graphplot.

Найдите кратчайший путь между узлом 1 и узлом 5. Поскольку несколько пар узлов имеют более одного ребра между ними, задайте три выхода, чтобы shortestpath чтобы вернуть определенные ребра, по которым проходит кратчайший путь.

[P,d,edgepath] = shortestpath(G,1,5)
P = 1×5

     1     2     4     3     5

d = 11
edgepath = 1×4

     1     7     9    10

Результаты показывают, что самый короткий путь имеет общую длину 11 и следует по краям, заданным G.Edges(edgepath,:).

G.Edges(edgepath,:)
ans=4×2 table
    EndNodes    Weight
    ________    ______

     1    2       2   
     2    4       3   
     3    4       1   
     3    5       5   

Выделите это ребро пути при помощи highlight функция со 'Edges' Пара "имя-значение" для задания индексов пройденных кромок.

highlight(p,'Edges',edgepath)

Figure contains an axes. The axes contains an object of type graphplot.

Найдите кратчайший путь между узлами в графике, используя расстояние между узлами в качестве веса ребер.

Создайте графиков с 10 узлами.

s = [1 1 2 2 3 4 4 4 5 5 6 6 7 8 9];
t = [2 4 3 5 6 5 7 9 6 7 7 8 9 10 10];
G = graph(s,t);

Создайте координаты x и y для узлов графика. Затем постройте график с помощью координат узла путем определения 'XData' и 'YData' Пары "имя-значение".

x = [1 2 3 2 2.5 4 3 5 3 5];
y = [1 3 4 -1 2 3.5 1 3 0 1.5];
plot(G,'XData',x,'YData',y)

Figure contains an axes. The axes contains an object of type graphplot.

Добавьте веса кромок к графику путем вычисления евклидовых расстояний между узлами графика. Расстояние вычисляется из координат узла (xi,yi) как:

d=|Δx|2+|Δy|2=|xs-xt|2+|ys-yt|2.

Вычислять Δx и Δy, первое использование findedges для получения векторов sn и tn описание исходного и целевого узлов каждого ребра в графике. Затем используйте sn и tn для индекса в векторы координат X и Y и вычисления Δx=xs-xt и Δy=ys-yt. The hypot функция вычисляет квадратуру суммы квадратов, поэтому задайте Δx и Δy как входные параметры для вычисления длины каждого ребра.

[sn,tn] = findedge(G);
dx = x(sn) - x(tn);
dy = y(sn) - y(tn);
D = hypot(dx,dy);

Добавьте расстояния к графику в качестве весов ребер и повторите график с отмеченными ребрами.

G.Edges.Weight = D';
p = plot(G,'XData',x,'YData',y,'EdgeLabel',G.Edges.Weight);

Figure contains an axes. The axes contains an object of type graphplot.

Вычислите самый короткий путь между узлом 1 и узлом 10 и задайте два выхода, чтобы также вернуть длину пути. Для взвешенных графиков, shortestpath автоматически использует 'positive' метод, учитывающий веса кромок.

[path,len] = shortestpath(G,1,10)
path = 1×4

     1     4     9    10

len = 6.1503

Используйте highlight функция для отображения пути на графике.

highlight(p,path,'EdgeColor','r','LineWidth',2)

Figure contains an axes. The axes contains an object of type graphplot.

Входные параметры

свернуть все

Входной график, заданный как graph или digraph объект. Использование graph для создания неориентированного графа или digraph для создания ориентированного графа.

Пример: G = graph(1,2)

Пример: G = digraph([1 2],[2 3])

Исходные и целевые идентификаторы узла, заданные как отдельные аргументы индексов узлов или имен узлов.

ЗначениеПример
Скалярный индекс узла1
Имя узла вектора символов'A'
Строковое скалярное имя узла"A"

Пример: shortestpath(G,2,5) вычисляет кратчайший путь между узлом 2 и узлом 5.

Пример: shortestpath(G,'node1','node2') вычисляет кратчайший путь между именованными узлами node1 и node2.

Алгоритм кратчайшего пути, заданный как один из опций в таблице.

ОпцияОписание
'auto' (по умолчанию)

The 'auto' опция автоматически выбирает алгоритм:

  • 'unweighted' используется для graph и digraph входы без весов кромок.

  • 'positive' используется для всех graph входы, которые имеют веса кромок и требуют, чтобы веса были неотрицательными. Эта опция также используется для digraph входы с неотрицательными весами кромок.

  • 'mixed' используется для digraph входы, веса которых содержат некоторые отрицательные значения. График не может иметь отрицательных циклов.

'unweighted'

Breadth - первый расчет, которое рассматривает все веса ребер как 1.

'positive'

Алгоритм Дейкстры, который требует, чтобы все веса ребер были неотрицательными.

'mixed' (только для digraph)

Алгоритм Беллмана-Форда для ориентированных графов, который требует, чтобы график не имел отрицательных циклов.

Пока 'mixed' медленнее 'positive' для той же задачи, 'mixed' является более универсальным, так как позволяет некоторым весам ребер быть отрицательными.

'acyclic' (только для digraph)

Алгоритм, разработанный для улучшения эффективности ориентированных ациклических графиков (ДАГ) с взвешенными ребрами.

Использовать isdag чтобы подтвердить, является ли ориентированный граф ациклическим.

Примечание

Для большинства графиков 'unweighted' является самым быстрым алгоритмом, далее следуют 'acyclic', 'positive', и 'mixed'.

Пример: shortestpath(G,s,t,'Method','acyclic')

Выходные аргументы

свернуть все

Самый короткий путь между узлами, возвращенный как вектор индексов узлов или массив имен узлов. P пуст, {}, если между узлами нет пути.

  • Если s и t содержать числовые индексы узлов, затем P является числовым вектором индексов узлов.

  • Если s и t содержать имена узлов, затем P - массив ячеек или строковые массивы, содержащий имена узлов.

Если между s несколько кратчайших путей и t, затем P содержит только один из путей. Возвращаемый путь может измениться в зависимости от того, какой алгоритм Method задает.

Кратчайшее расстояние пути, возвращаемое как числовой скаляр. d - суммирование весов ребер между последовательными узлами в P. Если между узлами нет пути, то d является Inf.

Ребра на самом коротком пути, возвращенные как вектор индексов ребер. Для мультиграфиков этот выход указывает, какое ребро между двумя узлами находится на пути. Этот выход совместим с 'Edges' пара "имя-значение" highlight, для примера: highlight(p,'Edges',edgepath).

Совет

  • The shortestpath, shortestpathtree, и distances функции не поддерживают неориентированные графы с отрицательными весами ребер или вообще любой график, содержащий отрицательный цикл, по этим причинам:

    • Отрицательный цикл - это путь, который ведет от узла назад к себе, при этом сумма весов ребер на пути отрицательная. Если отрицательный цикл находится на пути между двумя узлами, то между узлами не существует кратчайшего пути, поскольку более короткий путь всегда можно найти, пройдя отрицательный цикл.

    • Один отрицательный вес ребра в неориентированном графе создает отрицательный цикл.

Введенный в R2015b