Online Judge | Problem Set | Authors | Online Contests | User | ||||||
---|---|---|---|---|---|---|---|---|---|---|
Web Board Home Page F.A.Qs Statistical Charts | Current Contest Past Contests Scheduled Contests Award Contest |
我好无耻啊 拿着别人的模板往上一套 就AC 不行要好好研究一下这个模板//费用流 #include<stdio.h> #include<string.h> const int MAX=5100; const int INF=1000000000; const int MOD=1000000; struct EDGE { int cap,cost,v,next; }edge[MOD]; int head[MAX],E,q[MOD]; bool used[MAX]; int pre[MAX],cur[MAX],dis[MAX]; void add_edge(int s,int t,int cap,int cost) { edge[E].cap=cap;//容量 edge[E].cost=cost;//费用 edge[E].next=head[s]; edge[E].v=t; head[s]=E++; } int min(int a,int b){return (a==-1||b<a)?b:a;} int SPFA(int s,int t,int n) {//运用的仍然是最大流算法的增流原理,唯必须选定最小费用的增流链增流 int f=-1,r=0; int i,v; q[r]=s; for(i=0;i<n;i++) dis[i]=INF; dis[s]=0; pre[s]=s; cur[s]=-1; memset(used,false,sizeof(bool)*n); used[s]=true; while(f!=r) { f++; if(f>=MOD)f-=MOD; s=q[f]; used[s]=false; for(i=head[s];i!=-1;i=edge[i].next) { v=edge[i].v; if(edge[i].cap>0&&dis[s]+edge[i].cost<dis[v]) {//这里是核心 要得到容量允许范围的的最小费用 dis[v]=dis[s]+edge[i].cost; pre[v]=s;//并且记录父亲节点便于下方函数的容量的改变 cur[v]=i; if(!used[v]) { used[v]=true; r++; if(r>=MOD)r-=MOD;//为了防止数据太多溢出 q[r]=v; } } } } return dis[t]; } int MinCost(int s,int t,int n) { int ans=0; int u,v,cap; int cost; while(1) { cost=SPFA(s,t,n); if(cost==INF)break; u=v=t; cap=-1; for(u=pre[u];v!=s;v=u,u=pre[u]) { cap=min(cap,edge[cur[v]].cap);//和sap算法很像 } ans+=cost*cap; u=v=t; for(u=pre[u];v!=s;v=u,u=pre[u]) { edge[cur[v]].cap-=cap; edge[cur[v]^1].cap+=cap; } } return ans; } int main() { int s=; int t=; E=0; memset(head,-1,sizeof(int)*(t+1)); } Followed by: Post your reply here: |
All Rights Reserved 2003-2013 Ying Fuchen,Xu Pengcheng,Xie Di
Any problem, Please Contact Administrator