HDU2389 Rain on your Parade 【二分图最大匹配+HK算法】
2017-07-31 18:35
495 查看
HDU2389 链接
[align=left]Sample Input[/align]
2
1
2
1 0 3
3 0 3
2
4 0
6 0
1
2
1 1 2
3 3 2
2
2 2
4 4
[align=left]Sample Output[/align]
Scenario #1:
2
Scenario #2:
2
题意:有n个人,和m把雨伞,每个人都有一个速度,问在t时间内,最大有多少人能找到一把伞。不会出现俩个人打一把伞。
分析;二分图最大匹配,首先想到匈牙利,但是这回TLE,这时要用HK算法(其实是一种优化的匈牙利算法)
HK算法是在匈牙利的基础上增加一个BFS,寻找最短的增广路(可以有多条),然后用匈牙利沿着BFS增广的道路,进行增边。
复杂度为O(sqrt(V)*E) ,二匈牙利算法是O(V*E)(V为点数,E为边数) (学习HK之前要先学匈牙利算法)
[align=left]Sample Input[/align]
2
1
2
1 0 3
3 0 3
2
4 0
6 0
1
2
1 1 2
3 3 2
2
2 2
4 4
[align=left]Sample Output[/align]
Scenario #1:
2
Scenario #2:
2
题意:有n个人,和m把雨伞,每个人都有一个速度,问在t时间内,最大有多少人能找到一把伞。不会出现俩个人打一把伞。
分析;二分图最大匹配,首先想到匈牙利,但是这回TLE,这时要用HK算法(其实是一种优化的匈牙利算法)
HK算法是在匈牙利的基础上增加一个BFS,寻找最短的增广路(可以有多条),然后用匈牙利沿着BFS增广的道路,进行增边。
复杂度为O(sqrt(V)*E) ,二匈牙利算法是O(V*E)(V为点数,E为边数) (学习HK之前要先学匈牙利算法)
#include<cstring> #include<cstdio> #include<iostream> #include<algorithm> #include<vector> #include<queue> using namespace std; const int INF=0x3f3f3f3f; struct edge { int x,y,v; }; edge a[3003],b[3003]; vector<int> g[3003]; int mx[3003],my[3003],dx[3003],dy[3003],dis,n,m; bool vis[3003]; int bfs() { dis=INF; memset(dx,-1,sizeof(dx)); memset(dy,-1,sizeof(dy)); queue<int> que; for(int i=1;i<=n;i++) if(mx[i]==-1) { que.push(i); dx[i]=0; } while(!que.empty()) { int x=que.front();que.pop(); if(dx[x]>dis)break; //每次找到长度为dis增广路后跳出循环 for(int i=0;i<g[x].size();i++) { int y=g[x][i]; if(dy[y]!=-1)continue; dy[y]=dx[x]+1; if(my[y]==-1)dis=dy[y]; //找到增广路后更新最小值 else { dx[my[y]]=dy[y]+1; que.push(my[y]); } } } return dis!=INF; } int dfs(int x) { for(int i=0;i<g[x].size();i++) {int y=g[x][i]; if(vis[y]||dy[y]!=dx[x]+1)continue; //要沿着BFS增广的路 vis[y]=true; if(my[y]!=-1&&dy[y]==dis)continue; if(my[y]==-1||dfs(my[y])) { my[y]=x; mx[x]=y; return 1; } } return 0; } int max_macth() { int ret=0; memset(my,-1,sizeof(my)); memset(mx,-1,sizeof(mx)); while(bfs()) { memset(vis,false,sizeof(vis)); for(int i=1;i<=n;i++) if(mx[i]==-1&&dfs(i))ret++; } return ret; } int len(int i,int j) { return (a[i].x-b[j].x)*(a[i].x-b[j].x)+(a[i].y-b[i].y)*(a[i].y-b[j].y); } int main() { int tat,t,cas=1; scanf(" 4000 %d",&tat); while(tat--) { scanf("%d",&t); scanf("%d",&n); for(int i=1;i<=n;i++) g[i].clear(); for(int i=1;i<=n;i++) { scanf("%d%d%d",&a[i].x,&a[i].y,&a[i].v); a[i].v*=t; } scanf("%d",&m); for(int i=1;i<=m;i++) scanf("%d%d",&b[i].x,&b[i].y); for(int i=1;i<=n;i++) for(int j=1;j<=m;j++) if(len(i,j)<=a[i].v*a[i].v) g[i].push_back(j); printf("Scenario #%d:\n",cas++); printf("%d\n\n",max_macth()); } return 0; }
相关文章推荐
- hdu2389 Rain on your Parade【二分图最大匹配-HK算法】
- Hdu2389 Rain on your Parade (HK二分图最大匹配)
- HDU 2389 Rain on your Parade / HUST 1164 4 Rain on your Parade(二分图的最大匹配)
- hdu 2389 Rain on your Parade(二分图最大匹配,Hopcroft-Karp)
- Rain on your Parade---hdu2389(HK求最大匹配)
- [HDOJ2389]Rain on your Parade(二分图最大匹配,HK算法)
- hdu2389 Rain on your Parade--HK算法 & 最大匹配数
- hdu Rain on your Parade 二分图最大匹配
- hdu2389 Rain on your Parade (最大匹配Hopcroft--Karp)
- hdu 2389 Rain on your Parade(最大匹配,Hopcroft-Karp算法模版)
- hdu 2389 Rain on your Parade【最大匹配】
- hdu2389 Rain on your Parade(二分匹配hopcroft-carp算法)
- Hopcroft-Karp 二分图HDU2389 Rain on your Parade
- HDU 2389 ——Rain on your Parade——————【Hopcroft-Karp求最大匹配、sqrt(n)*e复杂度】
- hdu 2389 Rain on your Parade(二分最大匹配HK算法)
- HDU-2389 Rain on your Parade(二分图之Hopcroft-Karp算法)
- HDU 2389 Rain on your Parade (HK二分图)
- hdu 2389 Rain on your Parade(二分匹配Hopcroft-Carp算法模版)
- HDU2389---Rain on your Parade (二分图匹配-HK算法)
- HDU 2389 Rain on your Parade(二分匹配+Hopcroft-Carp算法模板题)