标签:关键点 max turn code board span 匹配 oar http
传送门:http://acm.hdu.edu.cn/showproblem.php?pid=1281
解题思路:
这是一道二分匹配的问题,把坐标(x,y)看做一条边。
先求出最大的匹配数,在枚举删除每一条边,若匹配数减少,这条边就是关键边,也是关键点。
实现代码;
#include <iostream> #include <cstdio> #include <cstring> #include <vector> using namespace std; const int MAXN=105; int G[MAXN][MAXN]; bool used[MAXN]; int cx[MAXN],cy[MAXN]; int N; bool findpath(int u){ for(int i=1;i<=N;i++){ if(!used[i]&&G[u][i]){ used[i]=1; if(cy[i]==-1||findpath(cy[i])){ cx[u]=i; cy[i]=u; return 1; } } } return 0; } int MaxMatch(){ memset(cx,-1,sizeof(cx)); memset(cy,-1,sizeof(cy)); int res=0; for(int i=1;i<=N;i++) if(cx[i]==-1){ memset(used,0,sizeof(used)); res+=findpath(i); } return res; } int main(){ int M,K; int cnt=0; while(scanf("%d%d%d",&N,&M,&K)!=EOF){ memset(G,0,sizeof(G)); for(int i=0;i<K;i++){ int u,v; scanf("%d%d",&u,&v); G[u][v]=1; } int ans=MaxMatch(); int res=0; for(int i=1;i<=N;i++) for(int j=1;j<=N;j++){ if(G[i][j]==1){ G[i][j]=0; if(MaxMatch()<ans) res++; G[i][j]=1; } } printf("Board %d have %d important blanks for %d chessmen.\n",++cnt,res,ans); } }
标签:关键点 max turn code board span 匹配 oar http
原文地址:http://www.cnblogs.com/IKnowYou0/p/6549520.html