Skip to content

Commit da6fd9a

Browse files
committed
feat: python impl for 0-1 BFS
1 parent 7a9c1c9 commit da6fd9a

File tree

1 file changed

+71
-38
lines changed

1 file changed

+71
-38
lines changed

src/graph/01_bfs.md

Lines changed: 71 additions & 38 deletions
Original file line numberDiff line numberDiff line change
@@ -17,27 +17,44 @@ In this article we demonstrate how we can use BFS to solve the SSSP (single-sour
1717
We can develop the algorithm by closely studying Dijkstra's algorithm and thinking about the consequences that our special graph implies.
1818
The general form of Dijkstra's algorithm is (here a `set` is used for the priority queue):
1919

20-
```cpp
21-
d.assign(n, INF);
22-
d[s] = 0;
23-
set<pair<int, int>> q;
24-
q.insert({0, s});
25-
while (!q.empty()) {
26-
int v = q.begin()->second;
27-
q.erase(q.begin());
28-
29-
for (auto edge : adj[v]) {
30-
int u = edge.first;
31-
int w = edge.second;
32-
33-
if (d[v] + w < d[u]) {
34-
q.erase({d[u], u});
35-
d[u] = d[v] + w;
36-
q.insert({d[u], u});
20+
=== "C++"
21+
```cpp
22+
d.assign(n, INF);
23+
d[s] = 0;
24+
set<pair<int, int>> q;
25+
q.insert({0, s});
26+
while (!q.empty()) {
27+
int v = q.begin()->second;
28+
q.erase(q.begin());
29+
30+
for (auto edge : adj[v]) {
31+
int u = edge.first;
32+
int w = edge.second;
33+
34+
if (d[v] + w < d[u]) {
35+
q.erase({d[u], u});
36+
d[u] = d[v] + w;
37+
q.insert({d[u], u});
38+
}
3739
}
3840
}
39-
}
40-
```
41+
```
42+
=== "Python"
43+
```py
44+
from heapq import heappop, heappush
45+
46+
47+
d = [float("inf")] * n
48+
d[s] = 0
49+
q = [(0, s)]
50+
while q:
51+
dv, v = heappop(q)
52+
if dv == d[v]:
53+
for u, w in adj[v]:
54+
if d[v] + w < d[u]:
55+
d[u] = d[v] + w
56+
heappush(q, (d[u], u))
57+
```
4158

4259
We can notice that the difference between the distances between the source `s` and two other vertices in the queue differs by at most one.
4360
Especially, we know that $d[v] \le d[u] \le d[v] + 1$ for each $u \in Q$.
@@ -53,27 +70,43 @@ This structure is so simple, that we don't need an actual priority queue, i.e. u
5370
We can simply use a normal queue, and append new vertices at the beginning if the corresponding edge has weight $0$, i.e. if $d[u] = d[v]$, or at the end if the edge has weight $1$, i.e. if $d[u] = d[v] + 1$.
5471
This way the queue still remains sorted at all time.
5572

56-
```cpp
57-
vector<int> d(n, INF);
58-
d[s] = 0;
59-
deque<int> q;
60-
q.push_front(s);
61-
while (!q.empty()) {
62-
int v = q.front();
63-
q.pop_front();
64-
for (auto edge : adj[v]) {
65-
int u = edge.first;
66-
int w = edge.second;
67-
if (d[v] + w < d[u]) {
68-
d[u] = d[v] + w;
69-
if (w == 1)
70-
q.push_back(u);
71-
else
72-
q.push_front(u);
73+
=== "C++"
74+
```cpp
75+
vector<int> d(n, INF);
76+
d[s] = 0;
77+
deque<int> q;
78+
q.push_front(s);
79+
while (!q.empty()) {
80+
int v = q.front();
81+
q.pop_front();
82+
for (auto edge : adj[v]) {
83+
int u = edge.first;
84+
int w = edge.second;
85+
if (d[v] + w < d[u]) {
86+
d[u] = d[v] + w;
87+
if (w == 1)
88+
q.push_back(u);
89+
else
90+
q.push_front(u);
91+
}
7392
}
7493
}
75-
}
76-
```
94+
```
95+
=== "Python"
96+
```py
97+
d = [float("inf")] * n
98+
d[s] = 0
99+
q = deque([s])
100+
while q:
101+
v = q.popleft()
102+
for u, w in adj[v]:
103+
if d[v] + w < d[u]:
104+
d[u] = d[v] + w
105+
if w == 1:
106+
q.append(u)
107+
else:
108+
q.appendleft(u)
109+
```
77110

78111
## Dial's algorithm
79112

0 commit comments

Comments
 (0)