POJ 3422 Kaka's Matrix Travels(最小费用最大流+拆点)
2013-02-27 11:21
288 查看
题目链接
关键在于建图,昨天做的的时候直接想错了。放了放,在路上和gyx讨论了一下,他说是不是拆点,我一想真是啊。。。
然后想了想建图的细节。。。今天写了程序,居然把电脑给写挂了。。第一次啊,可见程序写的多不靠谱啊。。
把一个点拆成两个点,这两个点之间的流量为1,费用为权值,这条边的起点和终点都可以连接下个位置的起点。
为了控制流量,多加了k个点,这多出来的k个点,到终点的流量为1,来控制最终的流量。剩下的就是模版了,改了一下求最大。
这样建图效率不是很高,想会不会超时。。。果真TLE了,不过数组开小了,开大之后,水过400+ms。。。
关键在于建图,昨天做的的时候直接想错了。放了放,在路上和gyx讨论了一下,他说是不是拆点,我一想真是啊。。。
然后想了想建图的细节。。。今天写了程序,居然把电脑给写挂了。。第一次啊,可见程序写的多不靠谱啊。。
把一个点拆成两个点,这两个点之间的流量为1,费用为权值,这条边的起点和终点都可以连接下个位置的起点。
为了控制流量,多加了k个点,这多出来的k个点,到终点的流量为1,来控制最终的流量。剩下的就是模版了,改了一下求最大。
这样建图效率不是很高,想会不会超时。。。果真TLE了,不过数组开小了,开大之后,水过400+ms。。。
#include <cstdio> #include <cstring> #include <cmath> #include <queue> using namespace std; #define INF 0x7fffffff int p[51][51]; int low[6001],path[6001]; int first[6001],in[6001],dis[6001]; int str,end,t; struct node { int u,v,w,cost,re,next; }edge[900001]; int ans; void CL() { t = 1; memset(first,-1,sizeof(first)); } void add(int u,int v,int w,int cost) { edge[t].u = u; edge[t].v = v; edge[t].w = w; edge[t].cost = cost; edge[t].re = t+1; edge[t].next = first[u]; first[u] = t ++; edge[t].u = v; edge[t].v = u; edge[t].w = 0; edge[t].cost = -cost; edge[t].re = t-1; edge[t].next = first[v]; first[v] = t ++; } int bfs() { int u,i,v; memset(path,-1,sizeof(path)); for(i = 0;i <= end;i ++) { dis[i] = -INF; in[i] = 0; } queue<int>que; que.push(str); dis[str] = 0; in[str] = 1; low[str] = INF; while(!que.empty()) { u = que.front(); in[u] = 0; que.pop(); for(i = first[u];i != -1;i = edge[i].next) { v = edge[i].v; if(edge[i].w&&dis[v] < dis[u]+edge[i].cost) { dis[v] = dis[u] + edge[i].cost; path[v] = i; low[v] = low[u] < edge[i].w ? low[u]:edge[i].w; if(!in[v]) { que.push(v); in[v] = 1; } } } } if(path[end] == -1) return -1; else return low[end]; } void mcmf() { int res,temp,now; while((res = bfs()) != -1) { now = end; while(now != str) { temp = path[now]; edge[temp].w -= res; edge[edge[temp].re].w += res; ans += res*edge[temp].cost; now = edge[temp].u; } } } int main() { int n,i,j,k; int x,y; ans = 0; CL(); scanf("%d %d",&n,&k); for(i = 1;i <= n;i ++) { for(j = 1;j <= n;j ++) scanf("%d",&p[i][j]); } str = 0; end = 2*n*n + k + 1; add(str,1,INF,0); for(i = 1;i <= n;i ++) { for(j = 1;j <= n;j ++) { x = (i-1)*n + j; y = x + n*n; add(x,y,1,p[i][j]); if(i + 1 <= n) { add(x,x+n,INF,0); add(y,x+n,INF,0); } if(j + 1 <= n) { add(x,x+1,INF,0); add(y,x+1,INF,0); } } } for(i = 1;i <= k;i ++) { add(x,2*n*n+i,INF,0); add(y,2*n*n+i,INF,0); add(2*n*n+i,end,1,0); } mcmf(); printf("%d\n",ans); return 0; }
相关文章推荐
- POJ-3422-Kaka's Matrix Travels(最小费用最大流)
- POJ 3422 Kaka's Matrix Travels(最小费用最大流)
- poj 3422 Kaka's Matrix Travels(最小费用最大流)
- poj 3422 Kaka's Matrix Travels 最小费最大流
- poj 3422 Kaka's Matrix Travels(最小费用最大流)
- POJ 3422 Kaka's Matrix Travels (最小费用最大流)
- POJ 3422 Kaka's Matrix Travels【最大费用流】
- poj 3422 Kaka's Matrix Travels(最小费用最大流)
- poj-3422-Kaka's Matrix Travels-最小费用最大流
- POJ Kaka's Matrix Travels 3422 (最小费用最大流)
- poj 3422 Kaka's Matrix Travels 费用流
- 【POJ 3422】 Kaka's Matrix Travels (最小费用最大流)
- POJ 3422 Kaka's Matrix Travels 最小费用最大流
- poj 3422 Kaka's Matrix Travels (最小费用最大流 模板)
- POJ 3422 Kaka's Matrix Travels 费用流
- POJ 3422 Kaka's Matrix Travels (最大费用最大流)
- poj 3422:Kaka's Matrix Travels(最小费用最大流)
- POJ3422 Kaka's Matrix Travels[费用流]
- poj3422 Kaka's Matrix Travels(最小费用最大流问题)
- POJ 3422 Kaka's Matrix Travels(拆点+最大流)