http://poj.org/problem?id=3422
题意 : 给你一个N*N的方格,每个格子有一个数字,让你从左上角开始走,只能往下往右走,走过的数字变为0,走K次,问最大能是多大,累加的。
思路 :http://blog.csdn.net/qq172108805/article/details/7857503,这道题挺难的,我也是看的题解。
#include <iostream> #include <stdio.h> #include <string.h> #include <queue> #include <stdlib.h> #include <algorithm> using namespace std; const int maxn = 5050 ; const int INF = 1000000000 ; const int maxm = 110000 ; struct node { int u,v,c,f,b,next ; }map[maxm] ; bool flag[maxn] ; int cap[55][55],dist[maxn],pre[maxn],head[maxn] ; int s,t,n,k,ans,cnt ; int del,val ; void addedge(int u,int v,int c,int b) { map[cnt].u = u ; map[cnt].v = v ; map[cnt].c = c ; map[cnt].b = b ; map[cnt].f = 0 ; map[cnt].next = head[u] ; head[u] = cnt++ ; map[cnt].u = v ; map[cnt].v = u ; map[cnt].c = 0 ; map[cnt].b = -b ; map[cnt].f = 0 ; map[cnt].next = head[v] ; head[v] = cnt++ ; } void spfa() { memset(flag,0,sizeof(flag)) ; queue<int >Q ; Q.push(s) ; flag[s] = true ; while(!Q.empty()) { int x = Q.front() ; Q.pop() ; flag[x] = false ; for(int i = head[x] ; i+1 ; i = map[i].next) { int y = map[i].v ; if(map[i].c > map[i].f && dist[y] < dist[x] + map[i].b) { dist[y] = dist[x]+map[i].b ; pre[y] = i ; if(!flag[y]) { flag[y] = true ; Q.push(y) ; } } } } } void mcmf() { for( ; ; ) { memset(dist,-1,sizeof(dist)) ; memset(pre,-1,sizeof(pre)) ; dist[s] = 0 ; spfa() ; if(dist[t] == -1) break ; int minn = INF ; for(int i = pre[t] ; i+1 ; i = pre[map[i].u]) minn = min(minn,map[i].c-map[i].f) ; for(int i = pre[t] ; i+1 ; i = pre[map[i].u]) { map[i].f += minn ; map[i^1].f -= minn ; } ans += dist[t] ; } } void Init() { cnt = 0 ; memset(head,-1,sizeof(head)) ; s = 0 ; t = 2*n*n+1 ; del = n*n ; ans = 0 ; } int main() { scanf("%d %d",&n,&k) ; Init() ; for(int i = 1 ; i <= n ; i++) { for(int j = 1 ; j <= n ; j++) scanf("%d",&cap[i][j]) ; } addedge(s,1,k,0) ; addedge(n*n+del,t,k,0) ; for(int i = 1 ; i <= n ; i++) { for(int j = 1 ; j <= n ; j++) { val = (i-1)*n+j ; addedge(val,val+del,1,cap[i][j]) ; addedge(val,val+del,INF,0) ; if(j != n) addedge(val+del,val+1,INF,0) ; if(i < n) addedge(val+del,val+n,INF,0) ; } } mcmf() ; printf("%d\n",ans) ; return 0; }