题意:

  给一个n*n的矩阵,每个格子中有正整数w[i][j],试为每行和每列分别确定一个数字row[i]和col[i],使得任意格子w[i][j]<=row[i]+col[j]恒成立。先输row,再输出col,再输出全部总和(总和应尽量小)。

思路:

  本题与匹配无关,但可以用KM算法解决。

  KM算法中的顶标就是保持了Lx[i]+ly[j]>=g[i][j]再求最大权和匹配的,但这个最大权和并没有关系。我们可以将row[i]看成一个男的,col[i]看成一个女的,这样男女的总数就相等。

  一般来说,Lx[i]或Ly[i]仅需要取该行/列中最大的那个数即可保证满足要求,但是这样太大了,可以通过调整来使得总和更小。而KM算法的过程就是一个调整的过程,每一对匹配的男女的那条边的权值就会满足等号 w[i][j]=row[i]+col[j],至少需要一个来满足等号,这样才能保证row[i]+col[j]是达到最小的,即从j列看,col[j]满足条件且最小,从i行看,row[i]满足条件且最小。这刚好与KM算法求最大权和一样。

 #include <bits/stdc++.h>
#define LL long LONG_LONG_MAX
#define INF 0x7f7f7f7f
#define LL long long
using namespace std;
const int N=; int grid[N][N], girl[N];
int Lx[N], Ly[N], slack[N];
bool S[N], T[N];
int n; bool DFS(int x)
{
S[x]=true;
for(int i=; i<=n; i++)
{
if(T[i]) continue;
int tmp=Lx[x]+Ly[i]-grid[x][i];
if(tmp==)
{
T[i]=true;
if(girl[i]== || DFS(girl[i]))
{
girl[i]=x;
return true;
}
}
else if(tmp<slack[i])
slack[i]=tmp;
}
return false;
} int KM()
{
memset(girl, , sizeof(girl));
memset(Lx, , sizeof(Lx));
memset(Ly, , sizeof(Ly));
for(int i=; i<=n; i++)
for(int j=; j<=n; j++)
Lx[i]=max(Lx[i], grid[i][j]); for(int i=; i<=n; i++) //对于每个树
{
for(int j=; j<=n; j++) slack[j]=INF;
while()
{
memset(S, , sizeof(S));
memset(T, , sizeof(T));
if( DFS(i) ) break; //找到匹配的蚂蚁 int d=INF;
for(int j=; j<=n; j++) //找最小D
{
if(!T[j] && d>slack[j])
d=slack[j];
} for(int j=; j<=n; j++) //更新树
{
if(S[j])
Lx[j]-=d;
} for(int j=; j<=n; j++) //更新蚂蚁
{
if(T[j]) Ly[j]+=d;
else slack[j]-=d;
}
}
}
int sum=;
for(int i=; i<=n; i++) sum+=Lx[i]+Ly[i];
return sum;
} int main()
{
freopen("input.txt", "r", stdin);
while(~scanf("%d",&n))
{
memset(grid, , sizeof(grid));
for(int i=; i<=n; i++)
for(int j=; j<=n; j++)
scanf("%d",&grid[i][j]); int ans=KM();
printf("%d", Lx[]);//值得注意的输出格式。
for(int i=; i<=n; i++) printf(" %d", Lx[i]);
printf("\n");
printf("%d",Ly[]);
for(int i=; i<=n; i++) printf(" %d", Ly[i]);
printf("\n");
printf("%d\n", ans);
}
return ;
}

AC代码

UVA 11383 Golden Tiger Claw 金虎爪(KM算法)的更多相关文章

  1. UVA 11383 - Golden Tiger Claw(二分图完美匹配扩展)

    UVA 11383 - Golden Tiger Claw 题目链接 题意:给定每列和每行的和,给定一个矩阵,要求每一个格子(x, y)的值小于row(i) + col(j),求一种方案,而且全部行列 ...

  2. uva11383 Golden Tiger Claw 深入理解km算法

    /** 题目: uva11383 Golden Tiger Claw 深入理解km算法 链接:https://vjudge.net/problem/UVA-11383 题意:lv 思路:lrj训练指南 ...

  3. 【KM算法】UVA 11383 Golden Tiger Claw

    题目大意 给你一个\(n×n\)的矩阵G,每个位置有一个权,求两个一维数组\(row\)和\(col\),使\(row[i] + col[j]\ge G[i][j]\),并且\(∑row+∑col\) ...

  4. UVA 11383 Golden Tiger Claw 题解

    题目 --> 题解 其实就是一个KM的板子 KM算法在进行中, 需要满足两个点的顶标值之和大于等于两点之间的边权, 所以进行一次KM即可. KM之后, 顶标之和就是最小的.因为如果不是最小的,就 ...

  5. Uva - 11383 - Golden Tiger Claw

    题意:一个N*N的矩阵,第i行第j列的元素大小为w[i][j],每行求一个数row[i],每列求一个数col[j],使得row[i] + col[j] >= w[i][j],且所有的row[]与 ...

  6. UVA 11383 Golden Tiger Claw(最佳二分图完美匹配)

    题意:在一个N*N的方格中,各有一个整数w(i,j),现在要求给每行构造row(i),给每列构造col(j),使得任意w(i,j)<=row(i)+col(j),输出row(i)与col(j)之 ...

  7. 【UVA11383】 Golden Tiger Claw 【二分图KM算法(板子)】

    题目 题目传送门:https://www.luogu.com.cn/problem/UVA11383 分析 最近刚刚学了二分图,然后来了一个这样的题,看完题意之后,稍微想一想就能想出来是一个二分图,然 ...

  8. 【UVA 11383】 Golden Tiger Claw (KM算法副产物)

    Omi, Raymondo, Clay and Kimiko are on new adventure- in search of new Shen Gong Wu. But EvilBoy Geni ...

  9. UVA11383 Golden Tiger Claw

    题目 UVA11383 Golden Tiger Claw 做法 \(KM\)好题啊,满足所有边\(l(x)+l(y)≥w(x,y)\)(个人理解,如不对请及时留言),这样能满足\(\sum\limi ...

随机推荐

  1. isMobile 一个简单的JS库,用来检测移动设备

    点这里 github地址:https://github.com/kaimallea/isMobile Example Usage I include the minified version of t ...

  2. 深入浅出ES6(十四):let和const

    作者 Jason Orendorff  github主页  https://github.com/jorendorff 回溯到1995年,当Brendan Eich在设计第一版JavaScript时, ...

  3. (1)在sina app engine 上建个人博客

    为啥想起来搞这一块呢? 有个哥们在新浪云上做了一个博客,有个师兄也做了这东西,我看挺炫酷的,也想做一个出来,把我在吉他,技术,摇滚,骑行,摄影方面的东西放到上面,也算是个个人简历,给人看也好看,比微博 ...

  4. Java-马士兵设计模式学习笔记-观察者模式-OOD 封装event

    把小孩醒来时的具体情况封装成事件类 Test.java class WakenUpEvent{ private long time; private String location; private ...

  5. Struts2笔记——利用token防止表单重复提交

    在一些项目中经常会让用户提交表单,当用户点击按钮提交后,如果再次浏览器刷新,这就会造成表单重复提交,若是提交的内容上传至服务器并请求数据库保存,重复提交的表单可能会导致错误,然后跳转到错误界面,这是一 ...

  6. C++:文件的输入和输出

    1.共同的打开文件方式: fin.open("test.txt",ios::binary) fout.open("test.txt",ios::binary) ...

  7. Data Flow ->> Fuzzy Lookup & Fuzzy Grouping

    这两个任务的作用是数据清洗(Data Cleansing). Fuzzy Lookup通过引用另外一张数据库表或者索引来进行相似值匹配.这种组件对于标准化和查找可能错误的客户端数据非常有用.例如像地址 ...

  8. javascript 中$符号是代表什么意思!

    $符号在php中是表示变量的特征字符, 在js中它也有很多作用, 一般我们用来命名一个函数名称,获取id的 1. 首先可以用来表示变量, 比如变量 var s='asdsd'或var $s='asda ...

  9. 使用ExtJs实现文件下载

    文件下载,是不可以直接通过Ext.Ajax.Request来实现的.一般的,可以通过创建一个隐藏的form表单来实现.具体代码以及代码注释如下: if (!Ext.fly('downForm')){ ...

  10. Java 全角字符转半角字符

    1.java代码里有时候会遇到代码注入的安全问题,为了防止这种问题,增加了一个过滤功能.主要是过滤全角字符,把url不能识别的全角字符转换成半角字符 public class Test { publi ...