Uvalive3353 Optimal Bus Route Design 带权二分图匹配
来源:互联网 发布:linux服务器宕机原因 编辑:程序博客网 时间:2024/06/05 00:57
题目描述:给出一个有向带权图,现在要求在图中找出若干个环,使得每个点恰好在一个环里,且所有环的距离之和最小,如果不能使每个点恰好在一个环里,输出"N"。
思路:
将每个点u拆成u和u'两个点,如果从u到v有一条权值为dist的边,那么就从u向v'连一条权值为dist的边,明显可以看出,现在的这个图是一个二分图。下面就是这个问题的关键——在这个二分图中,每一个完美匹配对应了原图中的一组互不相交且把每个点都囊括在内的环;反之也成立 ,即原图中的一组互不相交且把每个点都囊括在内的环正好对应了二分图中的一个完美匹配。为什么呢?因为在一组互不相交的环中,每个点的入度为一,出度为一;而在二分图的一个完美匹配中,一个点u的u对应一条边,u'对应一条边,即每个点u的入度为一,出度也为一,结论得证,因此,二分图中的一个完美匹配和原图中的一组互不相交的环一一对应。
分析到这里,做法就比较明朗了。原来是要求原图中的一组互不相交且把每个点都囊括在内的权值最小的环,现在就变成求一个权值最小的完美匹配,就是一个二分图带权匹配的问题。注意是最小匹配,每条边权应该取原来的相反数,不存在于图上的边设为-INF,跑二分图最大匹配就可以,跑完了结果取相反数,如果最终结果大于等于INF,就说明原图不存在完美匹配,那么输出“N”
理解:
这种转换如果是第一次见,似乎真的不太好想,见过一次之后就加以总结——二分图的一个匹配,对应于原图的一组互不相交的环,反之亦然
#include <bits/stdc++.h>#define LL long long#define mem(a , x) memset(a , x , sizeof(a))using namespace std;const int maxn = 100 + 5;const int INF = 1e5;int S[maxn] , T[maxn] , lx[maxn] , ly[maxn] , link[maxn] , slack[maxn];int mp[maxn][maxn] , n;int dfs(int u){ S[u] = 1; for(int i = 1 ; i <= n ; i++){ int d = lx[u] + ly[i] - mp[u][i]; if(!T[i] && d == 0){ T[i] = 1; if(link[i] == -1 || dfs(link[i])){ link[i] = u; return 1; } } else slack[i] = min(slack[i] , d); } return 0;}int KM(){ int res = 0; mem(link , -1); for(int i = 1 ; i <= n ; i++){ lx[i] = -INF; ly[i] = 0; for(int j = 1 ; j <= n ;j++){ lx[i] = max(lx[i] , mp[i][j]); } } for(int i = 1 ; i <= n ; i++){ mem(S , 0); mem(T , 0); for(int j = 1 ; j <= n ; j++) slack[j] = INF; while(!dfs(i)){ int d = INF; for(int j = 1 ; j <= n ;j++){ if(!T[j] && slack[j] < d){ d = slack[j]; } } for(int j = 1 ; j<= n ; j++){ if(S[j]){ lx[j] -= d; S[j] = 0; } if(T[j]){ ly[j] += d; T[j] = 0; } } } } for(int i = 1 ; i <= n ;i++){ res += (lx[i] + ly[i]); } return res;}int main(){ while(scanf("%d" , &n) != EOF && n){ for(int i = 1 ; i <= n ; i++){ for(int j = 1 ;j <= n ;j++){ mp[i][j] = -INF; } } int to , dis; for(int i = 1 ; i <= n ; i++){ while(scanf("%d" , &to) && to){ scanf("%d" ,&dis); mp[i][to] = -dis; } } int ans = -KM(); if(ans > 10000) puts("N"); else printf("%d\n" , ans); } return 0;}
阅读全文
0 0
- Uvalive3353 Optimal Bus Route Design 带权二分图匹配
- uva1349 Optimal Bus Route Design 费用流,二分图匹配
- UVALive - 3353 Optimal Bus Route Design(二分图最佳匹配)
- 1349 - Optimal Bus Route Design(二分图最小权完美匹配)
- UVA 1349 Optimal Bus Route Design (最小费用流 -- 二分图最小权完美匹配)
- LA 3353 Optimal Bus Route Design 二分匹配和有向图中的环
- UVa1349 Optimal Bus Route Design(二分图最佳完美匹配)
- UVA 1349 - Optimal Bus Route Design(KM完美匹配)
- uva 1349 - Optimal Bus Route Design(完美匹配)
- UVA 1349 Optimal Bus Route Design(最小权完美匹配)
- UVA 1349 Optimal Bus Route Design——最小权完美匹配
- Uva-1349-Optimal Bus Route Design
- UVa 1349 Optimal Bus Route Design
- UVA 1349 Optimal Bus Route Design
- LA 3353 Optimal Bus Route Design
- UVALive 3353 Optimal Bus Route Design
- Optimal Bus Route Design UVA 1349
- (beginer) UVA 最小费用流 1349Optimal Bus Route Design
- POJ
- Android 用ViewPager实现加载两个webview的可滑动Tab页
- 重构?先想好。
- 使用Maven自动打包配置文件生成开发环境,测试环境,生产环境
- java学习(11) 枚举enum
- Uvalive3353 Optimal Bus Route Design 带权二分图匹配
- MySQL主从配置详解
- Openstack之Nova创建虚机流程分析
- [leetcode]621. Task Scheduler
- 安装JDK1.8.0_73 配置JAVA的环境变量
- java android 占位符
- C#数组的使用
- 在CentOS 7上安装Kafka
- Mysql知识点记录