Перевод (Русский)

<topic>
## Восстановление кратчайшего пути
start = int(input())                    # начальная вершина
d = [-1] * n                            # расстояние от начальной вершины
p = [-1] * n                            # родительская вершина
q = deque([start])                      # очередь вершин
d[start] = 0                            # расстояние от start до start равно 0

while q:                                # пока очередь не пуста
    v = q.popleft()                     # достаём вершину из очереди
    print(v, end=' ')                   # выводим вершину
    for to in g[v]:                     # для всех вершин, смежных с v
        if d[to] == -1:                 # если вершина ещё не посещена
            d[to] = d[v] + 1            # (start -> to) = (start -> v) + 1
            p[to] = v                   # родитель вершины to — это v
            q.append(to)                # добавляем вершину в очередь

# Восстановление пути от start до end
end = int(input())                      # конечная вершина
path = []                               # путь от start до end
while end != -1:                        # пока есть родительская вершина
    path.append(end)                    # добавляем вершину в путь
    end = p[end]                        # переходим к родительской вершине

print(*path[::-1], sep=' -> ')          # выводим путь в обратном порядке
Итак, после добавления каждой вершины в очередь мы фиксируем её родителя в массиве p и в самом конце восстанавливаем маршрут, двигаясь от конечной вершины к начальной. В итоге путь нужно вывести в обратном порядке, потому что мы начинаем восстановление с конца и переходим по родителям к началу. Чтобы пройти от start до end, нам нужно развернуть полученный список.
Рассмотрим работу алгоритма на нескольких примерах:
n = 4, e = 4
На вход подаются пары (a, b): [(0, 1), (0, 2), (1, 2), (3, 2)]
Начальная вершина — 3, конечная вершина — 0
  1. p = [-1, -1, -1, -1], q = [3]
  1. v = 3, q = [] → добавить в очередь всех соседей, которые ещё не использованы
  1. p = [-1, -1, 3, -1], q = [2]
  1. v = 2, q = [] → добавить в очередь всех соседей, которые ещё не использованы
  1. p = [2, 2, 3, -1], q = [0, 1]
  1. v = 0, q = [1] → добавить в очередь всех соседей, которые ещё не использованы
  1. v = 1, q = [] → добавить в очередь всех соседей, которые ещё не использованы
  1. Восстановить путь
  1. end = 0 → end = 2 → end = 3
  1. Выводим 3 → 2 → 0
Обратите внимание: если в конце работы алгоритма d[end] всё ещё равно -1, это означает, что дойти до вершины end было невозможно.

Задача: Найти кратчайший маршрут

Интернет — это сеть компьютеров, соединённых друг с другом и способных передавать данные. Здесь эти компьютеры пронумерованы от 1 до n, и у нас есть информация о том, какие из них связаны напрямую. Алиса хочет отправить сообщение Бобу и желает выбрать путь, который позволит сделать это как можно быстрее. Значит, маршрут должен быть как можно короче.
Компьютеры Алисы и Боба имеют номера a и b соответственно. Требуется найти оптимальную последовательность компьютеров, по которым сообщение пройдёт от Alice к Bob за наименьшее время.

Входные данные

В первой строке содержатся два целых числа n (1 ≤ n ≤ 100 000) и e (1 ≤ e ≤ 100 000), обозначающие количество компьютеров и количество соединений в сети.
Во второй строке заданы два числа a и b (1 ≤ a, b ≤ n).
В следующих e строках содержатся пары целых чисел c1, c2 (1 ≤ c1, c2 ≤ n), указывающие, что компьютер c1 соединён с компьютером c2 и наоборот.

Выходные данные

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

Примеры

Вход
Выход
5 5 1 5 1 2 2 3 1 3 3 4 3 5
1 3 5
5 6 1 5 1 2 2 3 2 4 3 4 4 5 3 5
1 2 4 5
 

Constraints

Time limit: 2 seconds

Memory limit: 512 MB

Output limit: 1 MB

To check your solution you need to sign in
Sign in to continue