1
+ #include < vector>
2
+ #include < queue>
3
+
4
+ /*
5
+ usage : include this file in your project
6
+ If you want to test create an instance of the struct Dinic
7
+ pass in the appropriate arguments
8
+ call the flow() function
9
+ */
10
+
11
+ using namespace std ;
12
+
13
+ struct FlowEdge {
14
+ int v, u;
15
+ long long cap, flow = 0 ;
16
+ FlowEdge (int v, int u, long long cap) : v(v), u(u), cap(cap) {}
17
+ };
18
+
19
+ struct Dinic {
20
+ const long long flow_inf = 1e18 ;
21
+ vector<FlowEdge> edges;
22
+ vector<vector<int >> adj;
23
+ int n, m = 0 ;
24
+ int s, t;
25
+ vector<int > level, ptr;
26
+ queue<int > q;
27
+
28
+ Dinic (int n, int s, int t) : n(n), s(s), t(t) {
29
+ adj.resize (n);
30
+ level.resize (n);
31
+ ptr.resize (n);
32
+ }
33
+
34
+ void add_edge (int v, int u, long long cap) {
35
+ edges.emplace_back (v, u, cap);
36
+ edges.emplace_back (u, v, 0 );
37
+ adj[v].push_back (m);
38
+ adj[u].push_back (m + 1 );
39
+ m += 2 ;
40
+ }
41
+
42
+ bool bfs () {
43
+ while (!q.empty ()) {
44
+ int v = q.front ();
45
+ q.pop ();
46
+ for (int id : adj[v]) {
47
+ if (edges[id].cap - edges[id].flow < 1 )
48
+ continue ;
49
+ if (level[edges[id].u ] != -1 )
50
+ continue ;
51
+ level[edges[id].u ] = level[v] + 1 ;
52
+ q.push (edges[id].u );
53
+ }
54
+ }
55
+ return level[t] != -1 ;
56
+ }
57
+
58
+ long long dfs (int v, long long pushed) {
59
+ if (pushed == 0 )
60
+ return 0 ;
61
+ if (v == t)
62
+ return pushed;
63
+ for (int & cid = ptr[v]; cid < (int )adj[v].size (); cid++) {
64
+ int id = adj[v][cid];
65
+ int u = edges[id].u ;
66
+ if (level[v] + 1 != level[u] || edges[id].cap - edges[id].flow < 1 )
67
+ continue ;
68
+ long long tr = dfs (u, min (pushed, edges[id].cap - edges[id].flow ));
69
+ if (tr == 0 )
70
+ continue ;
71
+ edges[id].flow += tr;
72
+ edges[id ^ 1 ].flow -= tr;
73
+ return tr;
74
+ }
75
+ return 0 ;
76
+ }
77
+
78
+ long long flow () {
79
+ long long f = 0 ;
80
+ while (true ) {
81
+ fill (level.begin (), level.end (), -1 );
82
+ level[s] = 0 ;
83
+ q.push (s);
84
+ if (!bfs ())
85
+ break ;
86
+ fill (ptr.begin (), ptr.end (), 0 );
87
+ while (long long pushed = dfs (s, flow_inf)) {
88
+ f += pushed;
89
+ }
90
+ }
91
+ return f;
92
+ }
93
+ };
0 commit comments