1. 程式人生 > >最大流、最小割模板

最大流、最小割模板

sin memset edge pty bfs != std 結束 ons

純最大流,Dicnic算法:

 1 using namespace std;
 2 const int maxn=650;
 3 const int INF=0x3f3f3f3f;
 4 struct Edge{
 5     int from,to,cap,flow;
 6 };
 7 struct Dinic{
 8     int n,m,s,t;
 9     vector<Edge>edges;
10     vector<int>G[maxn];
11     bool vis[maxn];
12     int d[maxn];
13     int cur[maxn];
14 void AddEdge(int from,int to,int cap){ 15 edges.push_back((Edge){from,to,cap,0}); 16 edges.push_back((Edge){to,from,0,0}); 17 m=edges.size(); 18 G[from].push_back(m-2); 19 G[to].push_back(m-1); 20 } 21 bool BFS(){ 22 int x,i; 23 memset(vis,0
,sizeof(vis)); 24 queue<int>Q; 25 Q.push(s); 26 d[s]=0; 27 vis[s]=1; 28 while(!Q.empty()){ 29 x=Q.front(),Q.pop(); 30 for(i=0;i<G[x].size();i++){ 31 Edge & e =edges[G[x][i]]; 32 if(!vis[e.to]&&e.cap>e.flow){
33 vis[e.to]=1; 34 d[e.to]=d[x]+1; 35 Q.push(e.to); 36 } 37 } 38 } 39 return vis[t]; 40 } 41 int DFS(int x,int a){ 42 if(x==t||a==0) 43 return a; 44 int flow=0,f; 45 for(int &i=cur[x];i<G[x].size();i++){ 46 Edge & e=edges[G[x][i]]; 47 if(d[x]+1==d[e.to]&&(f=DFS(e.to,min(a,e.cap-e.flow)))>0){ 48 e.flow+=f; 49 edges[G[x][i]^1].flow-=f; 50 flow+=f; 51 a-=f; 52 if(a==0) 53 break; 54 } 55 } 56 return flow; 57 } 58 int Maxflow(int s,int t){ 59 this->s=s,this->t=t; 60 int flow=0; 61 while(BFS()){ 62 memset(cur,0,sizeof(cur)); 63 flow+= DFS(s,INF); 64 } 65 return flow; 66 } 67 };

Edmonds Karp模板

 1 const int maxn=;
 2 const int inf=0x3f3f3f3f;
 3 struct Edge
 4 {
 5     int from,to,cap,flow;
 6     Edge(int u,int v,int c,int f): from(u),to(v),cap(c),flow(f) {}
 7 };
 8 
 9 struct EdmondsKarp
10 {
11     int n,m;
12     vector<Edge> edges;
13     vector<int> G[maxn];
14     int a[maxn];
15     int p[maxn];
16 
17     void init(int n)
18     {
19       for(int i=0;i<n;i++) G[i].clear();
20       edges.clear();
21     }
22 
23     void AddEdge(int from,int to,int cap)
24     {
25        edges.push_back(Edge(from,to,cap,0));
26        edges.push_back(Edge(to,from,0,0));
27        m=edges.size();
28        G[from].push_back(m-2);
29        G[to].push_back(m-1);
30     }
31 
32    int Maxflow(int s,int t)
33    {
34      int flow=0;
35      while(1)
36      {
37         memset(a,0,sizeof(a));
38         queue<int> Q;
39         Q.push(s);
40         a[s]=inf;
41         while(!Q.empty())
42         {
43             int x=Q.front();Q.pop();
44             for(int i=0;i<G[x].size();i++)
45             {
46                 Edge& e=edges[G[x][i]];
47                 if(!a[e.to]&&e.cap>e.flow)
48                 {
49                     p[e.to]=G[x][i];
50                     a[e.to]=min(a[x],e.cap-e.flow);
51                     Q.push(e.to);
52                 }
53             }
54             if(a[t]) break;
55         }
56         if(!a[t]) break;
57         for(int u=t;u!=s;u=edges[p[u]].from)
58         {
59             edges[p[u]].flow+=a[t];
60             edges[p[u]^1].flow-=a[t];
61         }
62         flow+=a[t];
63     }
64     return flow;    
65    }
66 };

對於最小割來說,在算法結束後,令已經標號的結點(a[u]>0的結點)集合為S,其他集合為T=V-S,則(S,T)是圖 s-t 的最小割

最大流、最小割模板