Skip to content

Commit 7f71a91

Browse files
authored
Merge pull request #2770 from intagliated/add_dag_longest_path
feat(graph): add path reconstruction and return values to Bellman-Ford
2 parents e46c1a5 + c69bb69 commit 7f71a91

1 file changed

Lines changed: 52 additions & 0 deletions

File tree

‎algorithms/graph/bellman_ford.py‎

Lines changed: 52 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -76,3 +76,55 @@ def _initialize_single_source(
7676
distance[node] = float("inf")
7777
predecessor[node] = None
7878
distance[source] = 0
79+
80+
81+
82+
def bellman_ford_paths(
83+
graph: dict[str, dict[str, float]], source: str
84+
) -> tuple[dict[str, float] | None, dict[str, str | None] | None, bool]:
85+
"""Compute shortest-path distances and predecessors via Bellman-Ford."""
86+
distance: dict[str, float] = {}
87+
predecessor: dict[str, str | None] = {}
88+
89+
_initialize_single_source(graph, source, distance, predecessor)
90+
91+
num_vertices = len(graph)
92+
for _ in range(1, num_vertices):
93+
for current_node in graph:
94+
if distance[current_node] == float("inf"):
95+
continue
96+
for neighbor, edge_weight in graph[current_node].items():
97+
if distance[neighbor] > distance[current_node] + edge_weight:
98+
distance[neighbor] = distance[current_node] + edge_weight
99+
predecessor[neighbor] = current_node
100+
101+
for current_node in graph:
102+
if distance[current_node] == float("inf"):
103+
continue
104+
for neighbor, edge_weight in graph[current_node].items():
105+
if distance[neighbor] > distance[current_node] + edge_weight:
106+
return None, None, True
107+
108+
return distance, predecessor, False
109+
110+
111+
def reconstruct_shortest_path(
112+
predecessor: dict[str, str | None], source: str, target: str
113+
) -> list[str]:
114+
"""Rebuild the shortest path from *source* to *target*."""
115+
path: list[str] = []
116+
visited: set[str] = set()
117+
node: str | None = target
118+
119+
while node is not None and node not in visited:
120+
visited.add(node)
121+
path.append(node)
122+
if node == source:
123+
break
124+
node = predecessor.get(node)
125+
126+
if not path or path[-1] != source:
127+
return []
128+
129+
path.reverse()
130+
return path

0 commit comments

Comments
 (0)