POJ3422 Kaka's Matrix Travels 【费用流】*
POJ3422 Kaka’s Matrix Travels
Description
On an N × N chessboard with a non-negative number in each grid, Kaka starts his matrix travels with SUM = 0. For each travel, Kaka moves one rook from the left-upper grid to the right-bottom one, taking care that the rook moves only to the right or down. Kaka adds the number to SUM in each grid the rook visited, and replaces it with zero. It is not difficult to know the maximum SUM Kaka can obtain for his first travel. Now Kaka is wondering what is the maximum SUM he can obtain after his Kth travel. Note the SUM is accumulative during the K travels.
Input
The first line contains two integers N and K (1 ≤ N ≤ 50, 0 ≤ K ≤ 10) described above. The following N lines represents the matrix. You can assume the numbers in the matrix are no more than 1000.
Output
The maximum SUM Kaka can obtain after his Kth travel.
Sample Input
3 2
1 2 3
0 2 1
1 4 2
Sample Output
15
题意大概就是给你一个n*n的矩形,每一个方格中有一个权值,定义一次行走是从左上角走到右下角,而且每一次移动只能向右边或者下边移动,现在我们要行走k次,并使经过的点集的和最大(每个点值计算一次)
我们很容易想到把每个点的权值作为这个点某种意义上的费用(因为只能计算一次,后面会介绍建图方法),然后我们想最大化这个费用,所以对于这种问题我们可以见图的时候将边权取相反数,然后再跑出最小费用大流的时候将费用取相反数,不难发现这个时候的费用是最大化的
然后我们怎么处理一个节点的边权只能计算一次这个条件呢?
不妨这样思考,我们把一个点i拆成两个点i" role="presentation">ii和i+n∗n" role="presentation">i+n∗ni+n∗n,在i" role="presentation">ii和i+n∗n" role="presentation">i+n∗ni+n∗n之间连接两条弧:
1:一条容量为1,费用为负边权
2:一条容量为k-1,费用为0
我们可以很容易得到如果有流量经过弧2,一定有流量经过弧1,不然就不满足最小费用的性质
又对于两个节点i" role="presentation">ii和j" role="presentation">jj,满足j在i的下边或右边,即i" role="presentation">ii可以到达j" role="presentation">jj,那么我们可以把i+n∗n" role="presentation">i+n∗ni+n∗n连接到j" role="presentation">jj,这样流经i" role="presentation">ii的流量就可以流到j" role="presentation">jj了
现在我们只需要保证源点S流到第一个节点(坐标(1,1))的容量是k就好了
整理一下构图思路:
1 从S" role="presentation">SS连接到第一个节点(1,1)" role="presentation">(1,1)(1,1),容量为k
2 从i" role="presentation">ii到i+n∗n" role="presentation">i+n∗ni+n∗n连接两条弧:
" role="presentation"> 1:一条容量为1,费用为负边权
" role="presentation"> 2:一条容量为k-1,费用为0
3 对于i" role="presentation">ii到可以到达的j" role="presentation">jj连接一条从i+n∗n" role="presentation">i+n∗ni+n∗n到j" role="presentation">jj的边
4 从最后一个节点(n,n)" role="presentation">(n,n)(n,n)连接到汇点T" role="presentation">TT
#include<iostream>
#include<cstdio>
#include<cstring>
#include<vector>
#include<queue>
#include<algorithm>
using namespace std;
#define N 100010
#define INF 0x3f3f3f3f
struct Edge{
int u,v,cap,flow,cost;
Edge(int xu,int xv,int xcap,int xflow,int xcost){
u=xu;v=xv;cap=xcap;flow=xflow;cost=xcost;
}
};
struct MCMF{
int s,t,f[N],p[N],d[N];
bool inq[N];
vector<Edge> E;
vector<int> G[N];
void add(int u,int v,int cap,int cost){
E.push_back(Edge(u,v,cap,0,cost));
E.push_back(Edge(v,u,0,0,-cost));
int m=E.size();
G[u].push_back(m-2);
G[v].push_back(m-1);
}
bool SPFA(int &flow,int &cost){
memset(inq,0,sizeof(inq));
memset(d,0x3f,sizeof(d));
queue<int> Q;Q.push(s);
d[s]=0;f[s]=INF;
while(!Q.empty()){
int u=Q.front();Q.pop();
inq[u]=0;
for(int i=0;i<G[u].size();i++){
Edge e=E[G[u][i]];
if(d[e.v]>d[u]+e.cost&&e.cap>e.flow){
d[e.v]=d[u]+e.cost;
p[e.v]=G[u][i];
f[e.v]=min(f[u],e.cap-e.flow);
if(!inq[e.v]){
Q.push(e.v);
inq[e.v]=1;
}
}
}
}
if(d[t]==INF)return false;
flow+=f[t];cost+=f[t]*d[t];
int u=t;
while(u!=s){
E[p[u]].flow+=f[t];
E[p[u]^1].flow-=f[t];
u=E[p[u]].u;
}
return true;
}
int Min_cost_Max_flow(){
int flow=0,cost=0;
while(SPFA(flow,cost));
return cost;
}
}mcmf;
int n,k;
int g[100][100];
int Index(int x,int y){return (x-1)*n+y;}
int main(){
scanf("%d%d",&n,&k);
mcmf.s=0;mcmf.t=2*n*n+1;
mcmf.add(0,1,k,0);
for(int i=1;i<=n;i++){
for(int j=1;j<=n;j++){
scanf("%d",&g[i][j]);
int tmp=Index(i,j);
mcmf.add(tmp,tmp+n*n,1,-g[i][j]);
mcmf.add(tmp,tmp+n*n,k-1,0);
if(i<n){
int tmp1=Index(i+1,j);
mcmf.add(tmp+n*n,tmp1,INF,0);
}
if(j<n){
int tmp1=Index(i,j+1);
mcmf.add(tmp+n*n,tmp1,INF,0);
}
}
}
mcmf.add(2*n*n,2*n*n+1,k,0);
printf("%d",-mcmf.Min_cost_Max_flow());
return 0;
}
POJ3422 Kaka's Matrix Travels 【费用流】*的更多相关文章
- POJ3422 Kaka's Matrix Travels[费用流]
Kaka's Matrix Travels Time Limit: 1000MS Memory Limit: 65536K Total Submissions: 9522 Accepted: ...
- poj 3422 Kaka's Matrix Travels 费用流
题目链接 给一个n*n的矩阵, 从左上角出发, 走到右下角, 然后在返回左上角,这样算两次. 一共重复k次, 每个格子有值, 问能够取得的最大值是多少, 一个格子的值只能取一次, 取完后变为0. 费用 ...
- poj3422 Kaka's Matrix Travels(最小费用最大流问题)
/* poj3422 Kaka's Matrix Travels 不知道 k次 dp做为什么不对??? 看了大牛的代码,才知道还可以这样做! 开始没有理解将a 和 a‘ 之间建立怎样的两条边,导致程序 ...
- POJ3422 Kaka's Matrix Travels
描述 On an N × N chessboard with a non-negative number in each grid, Kaka starts his matrix travels wi ...
- POJ 3422 Kaka's Matrix Travels(费用流)
Kaka's Matrix Travels Time Limit: 1000MS Memory Limit: 65536K Total Submissions: 6792 Accepted: ...
- POJ 3422 Kaka's Matrix Travels
Kaka's Matrix Travels Time Limit: 1000MS Memory Limit: 65536K Total Submissions: 9567 Accepted: ...
- POJ 3422 Kaka's Matrix Travels (K取方格数:最大费用流)
题意 给出一个n*n大小的矩阵,要求从左上角走到右下角,每次只能向下走或者向右走并取数,某位置取过数之后就只为数值0,现在求解从左上角到右下角走K次的最大值. 思路 经典的费用流模型:K取方格数. 构 ...
- [poj] 3422 Kaka's Matrix Travels || 最小费用最大流
原题 给一个N*N的方阵,从[1,1]到[n,n]走K次,走过每个方格加上上面的数,然后这个格上面的数变为0.求可取得的最大的值. 要求最大值,所以把边权全为负跑最小费用即可.因为只有第一次经过该点的 ...
- POJ3422或洛谷2045 Kaka's Matrix Travels
POJ原题链接 洛谷原题链接 很裸的费用流. 将每个点\(x\)拆成\(x_1,x_2\),并从\(x_1\)向\(x_2\)连一条容量为\(1\),费用为该点的权值的边,以及一条容量为\(+\inf ...
随机推荐
- Vuex访问状态对象的方法
除了<Vuex最基本样例>中的方法外,还有两种方法访问状态对象state: 只需要改app.vue文件 方法一:引入computed <template> <div id ...
- Outlook 配置qq邮箱账号
最近想用Outlook 2013管理QQ邮件,配置好久都没有成功,结果最后发现第三方登陆QQ邮箱不使用QQ密码,而是使用一个叫”授权码”的东西.(用户名自动生成的,授权码就填这,报错后填会测试不通过) ...
- sass的多种用法
sass的多种用法 主要归纳总结sass的常见用法,作为个人笔记使用,部分知识点并不仔细讲解.具体可参考文档:sass官网 一.嵌套 .svg{ position: absolute; left: 0 ...
- Knockout结合Bootstrap创建动态UI--产品列表管理
本篇文章结合Bootstrap创建一个比较完整的应用,对产品列表进行管理,包括产品的增加.删除.修改. 需要的引用 <script type='text/javascript' src='htt ...
- 设计模式--备忘录模式C++实现
备忘录模式C++实现 1定义Memento pattern 在不破坏封装性的前提下,捕获一个对象的内部状态,并在该对象之外保存这个状态.这样以后就可以将该对象恢复到原先的状态 2类图 3实现 clas ...
- JAVA常用数据结构API
Quene
- 无密码登陆的ssh和ssh-agent
原文地址:http://lxshopping.blog.51cto.com/4542643/1179864/ 一,不需要输密码的ssh 原理:首先服务器端把公钥传给Client端,Client端在验证 ...
- mysql中的tinyint在C#中的类型
mysql中的tinyint在C#中的类型 在C#中对应的类型是System.SByte,不是byte.
- 【hdu1005】Number Sequence
题目描述 一个数列的定义如下: f(1) = 1, f(2) = 1, f(n) = (A * f(n - 1) + B * f(n - 2)) mod 7. 给出A和B,你要求出f(n). 输入 输 ...
- Server.Transfer 页面之间传值
server.transfer 特点: 1:大家熟悉的一个特点,用server.transfer 跳转到新页面时,浏览器的地址是没有改变的(因为重定向完全在服务器端进行,浏览器根本不知道服务器已经执行 ...