Max stream of POJ 3204
Question: Which side can be added to increase the overall traffic.
Obviously, increasing the capacity of a single edge changes the global capacity. After a maximum stream is reached, these edges may only appear in the edge of the full stream, it is also the only full stream edge in a path.
Question: The public solution. After a maximum stream is reached, the entire graph is broken. The full stream edge is recorded, and the full stream edge is searched from the starting point, and only the non-full stream edge is taken, search from the end point and only take the non-full edge. If the starting point of a full edge is marked by the start point and the end point is marked by the end point, then, this full stream edge exists in a non-full stream route with its own starting point and ending point. This edge is the key edge, Num ++;
My practice: Since the entire graph is running after the maximum flow, if you add traffic to some key sides, a new path from the start point to the end point will appear, we can directly add a stream in the residual network, and then perform a wide search from the start point to the end point. If we can reach num ++, the idea is simple, but due to multiple extensive searches, if you use a common queue to implement dinic, it will time out. Although it is not good to use arrays to simulate the queue, it means it does save time.
Code:
# Include
# Include
# Include
# Define INF 1000000000
# Define N 1005
# Define M 10005
Using namespace std;
Int tot, list [N], deep [N], n, m, q [2000005];
Struct Node
{
Int date, value, next, from;
} Cun [2, 2000005];
Struct dian
{
Int x, t;
} Old, xin;
Void add (int a, int B, int c)
{
Cun [++ tot]. value = c;
Cun [tot]. date = B;
Cun [tot]. next = list [a];
Cun [tot]. from =;
List [a] = tot;
Cun [++ tot]. value = 0;
Cun [tot]. date =;
Cun [tot]. next = list [B];
Cun [tot]. from = B;
List [B] = tot;
}
Int BFS (int s, int t)
{
Int I, x, v, tail = 0, head = 0;
Memset (deep, 255, sizeof (deep ));
Deep [s] = 0;
Q [tail ++] = s;
While (head {
X = q [head ++];
For (I = list [x]; I = cun [I]. next)
{// Printf ("! \ N ");
If (cun [I]. value & deep [v = cun [I]. date] =-1)
{
Deep [v] = deep [x] + 1;
If (v = t)
Return 1;
Q [tail ++] = v;
}
}
}
Return 0;
}
Int mmin (int a, int B)
{
If ( Else return B;
}
Int DFS (int s, int t, int min)
{
If (s = t) return min;
Int neww = 0;
For (int k = list [s]; k = cun [k]. next)
{
Int c = cun [k]. value;
Int date = cun [k]. date;
If (c = 0 | deep [date]! = Deep [s] + 1) continue;
Int m = DFS (date, t, mmin (c, min-neww ));
Neww + = m;
Cun [k]. value-= m;
Cun [k ^ 1]. value + = m;
If (neww = min) break;
}
If (neww = 0) deep [s] = 0;
Return neww;
}
Int dinic (int s, int t, int n)
{
Int num = 0;
While (BFS (s, t ))
{
Num + = DFS (s, t, INF );
}
Return num;
}
Void bulid ()
{
Int a, B, c;
For (int I = 0; I <m; I ++)
{
Scanf ("% d", & a, & B, & c );
Add (a + 1, B + 1, c );
}
Int k = dinic (1, n, n + 5 );
Int num = 0;
For (int I = 2; I <= tot; I + = 2)
{
If (! Cun [I]. value)
{
Cun [I]. value + = 1;
If (BFS (1, n) num ++;
Cun [I]. value-= 1;
}
}
Printf ("% d \ n", num );
}
Int main ()
{
While (scanf ("% d", & n, & m )! = EOF)
{
Memset (list, 0, sizeof (list ));
Tot = 1;
Bulid ();
}
}