最小费用流

zkw费用流+当前弧优化

 1 var
 2   o,v:array[0..1600] of boolean;
 3   f,s,d,dis:array[0..1600] of longint;
 4   next,p,c,w:array[-100000..100000] of longint;
 5   i,j,k,l,y,t,ss,tt,n,ans,imp,flow:longint;
 6 procedure link(i,j,k,l:longint);
 7 begin
 8   inc(t);
 9   next[t]:=d[i]; d[i]:=t; p[t]:=j; c[t]:=k; w[t]:=l;
10   next[-t]:=d[j]; d[j]:=-t; p[-t]:=i; w[-t]:=-l;
11 end;
12 function dfs(i,flow:longint):longint;
13 var j,k,l,min:longint;
14 begin
15   if i=tt then
16   begin
17     inc(ans,dis[i]*flow); exit(flow);
18   end;
19   k:=s[i]; j:=p[k]; dfs:=0;
20   o[i]:=true; v[i]:=true;
21   while k<>0 do
22   begin
23     l:=dis[i]+w[k]-dis[j]; min:=flow;
24     if c[k]<min then min:=c[k];
25     if(min>0)and(l<f[j])then f[j]:=l;
26     if(min>0)and(l=0)and(not o[j])then
27     begin
28       l:=dfs(j,min);
29       inc(dfs,l); dec(flow,l);
30       dec(c[k],l); inc(c[-k],l);
31     end;
32     if flow=0 then break;
33     s[i]:=next[s[i]];
34     k:=s[i]; j:=p[k];
35   end;
36   o[i]:=false;
37 end;
38 begin
39   build;
40   repeat
41     for i:=ss to tt do s[i]:=d[i];
42     fillchar(v,sizeof(v),false);
43     fillchar(f,sizeof(f),1);
44     inc(flow,dfs(ss,1 shl 20));
45     imp:=1 shl 20;
46     for i:=ss to tt do
47     if(not v[i])and(f[i]<imp)then imp:=f[i];
48     for i:=ss to tt do if not v[i] then inc(dis[i],imp);
49   until imp=1 shl 20;
50   writeln(ans);
51 end.
PASCAL
 1 #include<bits/stdc++.h>
 2 using namespace std;
 3 const int INF=1000000000;
 4 int o[1600],v[1600],f[1600],c[1600],s[1600],dis[1600];
 5 int b[200001],p[200001],d[200001],w[200001];
 6 int j,k,ss,tt,n,ans,imp,flow,cnt;
 7 void link(int i,int j,int k,int l)
 8 {
 9     cnt++; b[cnt]=c[i]; c[i]=cnt; p[cnt]=j; d[cnt]=k; w[cnt]=l;
10     cnt++; b[cnt]=c[j]; c[j]=cnt; p[cnt]=i; d[cnt]=0; w[cnt]=-l;
11 }
12 int dfs(int x,int flow)
13 {
14     if(x==tt){ ans+=dis[x]*flow; return flow; }
15     int ans2=0; o[x]=1; v[x]=1;
16     for(int i=s[x];i;i=b[i])
17     {
18         int j=p[i]; int l=dis[x]+w[i]-dis[j]; int mi=min(flow,d[i]);
19         if((mi>0)and(l<f[j]))f[j]=l;
20         if((mi>0)and(l==0)and(!o[j]))
21         {
22             l=dfs(j,mi);
23             ans2+=l; flow-=l; d[i]-=l; d[i^1]+=l;
24         }
25         if(flow==0)break; s[x]=b[s[x]];
26     }
27     o[x]=0; return ans2;
28 }
29 int main()
30 {
31     cnt=1; build;
32     while(1)
33     {
34         for(int i=ss;i<=tt;i++)s[i]=c[i];
35         memset(v,0,sizeof(v)); for(int i=ss;i<=tt;i++)f[i]=INF;
36         flow+=dfs(ss,INF); imp=INF;
37         for(int i=ss;i<=tt;i++)if((!v[i])and(f[i]<imp))imp=f[i];
38         if(imp==INF)break;
39         for(int i=ss;i<=tt;i++)if(!v[i])dis[i]+=imp;
40     }
41     printf("%d %d\n",flow,ans);
42 }
C++
posted @ 2017-01-05 15:56  GhoStreach  阅读(234)  评论(0编辑  收藏  举报