poj 3041 Asteroids

// 题意:N*N矩阵,有一些格子里有小行星,一颗炮弹能够消灭掉矩阵中一行或一列的全部小行星,
// 问消灭掉所有小行星所需的最小炮弹数目。
// 思路:令集合X和集合Y分别表示矩阵的行和列,将矩阵每一行看成集合X的点,每一列看成集合Y的点,
// 如果第i行第j列有小行星则将Xi和Yj连一条边,这样就构成一个二分图,
// 题目就是求二分图的最小覆盖点数(即最少的行和列),转化成二分图的最大匹配数

#include<iostream> //求二分图的最小覆盖点数
#include<cstring>
using namespace std;
int n;
int edge[510][510],vis[510],link[510];
int find(int a)
{
for(int i=1;i<=n;++i)
{
if(edge[a][i]&&!vis[i])
{
vis[i]=1;
if(link[i]==0||find(link[i]))
{
link[i]=a;
return 1;
}
}
}
return 0;
}
int main()
{
int k,r,c;
cin>>n>>k;
memset(edge,0,sizeof(edge));
memset(link,0,sizeof(link));
while(k--)
{
cin>>r>>c;
edge[r][c]=1; //第r行第c列有小行星,则将Xr和Yc连一条边
}
int ans=0;
for(int i=1;i<=n;++i)
{
memset(vis,0,sizeof(vis));
if(find(i))
ans++;
}
cout<<ans<<endl;
return 0;
}

posted on 2011-07-22 23:02  sysu_mjc  阅读(122)  评论(0编辑  收藏  举报

导航