POJ3204+DInic+maxflow
Dinic+maxflow
题意:找这样一种边的个数,就是增加该边的容量,可以使得最大流变大
思路:求maxflow,再枚举流量为0的边,增加容量,看是否能找到增广路径。
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
1 /* 2 Dinic+maxflow 3 题意:找这样一种边的个数,就是增加该边的容量,可以使得最大流变大 4 思路:求maxflow,再枚举流量为0的边,增加容量,看是否能找到增广路径。 5 */ 6 #include<stdio.h> 7 #include<string.h> 8 #include<stdlib.h> 9 #include<algorithm> 10 #include<iostream> 11 #include<queue> 12 #include<map> 13 #include<stack> 14 #include<set> 15 #include<math.h> 16 using namespace std; 17 typedef long long int64; 18 //typedef __int64 int64; 19 typedef pair<int64,int64> PII; 20 #define MP(a,b) make_pair((a),(b)) 21 const int maxn = 505; 22 const int maxm = 5005; 23 const int inf = 0x3f3f3f3f; 24 const double pi=acos(-1.0); 25 const double eps = 1e-8; 26 27 struct Edge{ 28 int u,v,next,val; 29 bool flag; 30 }edge[ maxm<<2 ]; 31 int cnt,head[ maxn ]; 32 int vis[ maxn ]; 33 int lev[ maxn ]; 34 int q[ maxn<<4 ]; 35 36 void init(){ 37 cnt = 0; 38 memset( head,-1,sizeof( head ) ); 39 } 40 void addedge( int a,int b,int c ){ 41 edge[ cnt ].u = a; 42 edge[ cnt ].v = b; 43 edge[ cnt ].val = c; 44 edge[ cnt ].next = head[ a ]; 45 if( cnt%2==0 ) edge[ cnt ].flag = true; 46 else edge[ cnt ].flag = false; 47 head[ a ] = cnt ++; 48 } 49 50 bool bfs( int n,int start,int end ){ 51 int head2 = 0,tail2 = 0; 52 q[ tail2++ ] = start; 53 memset( lev,-1,sizeof( lev ) ); 54 lev[ start ] = 0; 55 while( head2<tail2 ){ 56 int u = q[ head2++ ]; 57 for( int i=head[u];i!=-1;i=edge[i].next ){ 58 int v = edge[i].v; 59 if( edge[i].val>0&&lev[v]==-1 ){ 60 lev[v] = lev[u]+1; 61 q[ tail2++ ] = v; 62 } 63 } 64 } 65 if( lev[ end ]==-1 ) return false; 66 else return true; 67 } 68 69 int Dinic( int n,int start,int end ){ 70 int maxflow = 0; 71 while( true ){ 72 if( bfs(n,start,end )==false ) break; 73 int id = start; 74 int tail = 0; 75 while( true ){ 76 if( id==end ){ 77 int flow = inf; 78 int flag = -1; 79 for( int i=0;i<tail;i++ ){ 80 if( edge[ q[i] ].val<flow ){ 81 flow = edge[ q[i] ].val ; 82 flag = i; 83 } 84 } 85 for( int i=0;i<tail;i++ ){ 86 edge[ q[i] ].val -= flow; 87 edge[ q[i]^1 ].val += flow; 88 } 89 if( flag!=-1 ){ 90 maxflow += flow; 91 tail = flag; 92 id = edge[ q[flag] ].u; 93 } 94 else 95 return inf; 96 } 97 id = head[ id ]; 98 while( id!=-1 ){ 99 if( edge[id].val>0&&lev[edge[id].u]+1==lev[edge[id].v] ){ 100 break; 101 } 102 id = edge[ id ].next; 103 } 104 if( id!=-1 ){ 105 q[ tail++ ] = id; 106 id = edge[ id ].v; 107 } 108 else{ 109 if( tail==0 ) break; 110 lev[ edge[q[tail-1]].v ] = -1; 111 id = edge[ q[--tail] ].u; 112 } 113 } 114 } 115 return maxflow; 116 } 117 118 int main(){ 119 int n,m; 120 while( scanf("%d%d",&n,&m)==2 ){ 121 init(); 122 int a,b,c; 123 int start = 0; 124 int end = n-1; 125 for( int i=0;i<m;i++ ){ 126 scanf("%d%d%d",&a,&b,&c); 127 addedge( a,b,c ); 128 addedge( b,a,0 ); 129 } 130 Dinic( n,start,end ); 131 int ans = 0; 132 for( int i=0;i<cnt;i++ ){ 133 if( edge[i].val==0&&edge[i].flag==true ){ 134 edge[i].val ++ ; 135 if( bfs( n,start,end )==true ){ 136 ans ++ ; 137 } 138 edge[i].val -- ; 139 } 140 } 141 printf("%d\n",ans); 142 } 143 return 0; 144 }
keep moving...