您的位置:首页 > 其它

poj2594匈牙利算法+邻接表+传递闭包

2014-02-13 17:05 204 查看
题意:给你一个有向图,求最大路覆盖数,但是点可以重复;
解题思路:这题跟hdu 1054的不同之处是可以走重复的点,那么我们就可以这样想,假如这个点会被走重,那么我们就加一条边去跨过这个点,那么当这个点的相邻点集中,任意两个不相邻的点也能在匈牙利算法中得到匹配,最后在这个改造后的图中求最大路径覆盖数,就果断ac了
891msG++代码

#include<iostream>
#include<cstdio>
#include<cstdlib>
#include<cstring>
int mj[502][502];
int flag[502],result[502];
int n,m,k;
bool find(int i)
{
int j;
for(j=0;j<n;j++)
{
if(mj[i][j]!=0&&flag[j]==0)
{
flag[j]=1;
if(result[j]==0||find(result[j]))
{
result[j]=i;
return true;
}
}
}
return false;
}
void floyd()
{
int k,i,j;
for ( k = 0; k < n; k++)
for ( i = 0; i < n; i++)
for (j = 0; j < n; j++)
if (i != j && mj[i][k]==1 && mj[k][j]==1)
mj[i][j] = 1;
}
int main()
{
int i,ans,x,y;
while(scanf("%d %d",&n,&m),n||m)
{
memset(result,0,sizeof(result));
memset(mj,0,sizeof(mj));
for(i=0;i<m;i++)
{
scanf("%d %d",&x,&y);
x--;
y--;
mj[x][y]=1;
}
ans=0;
floyd();
for(i=0;i<n;i++)
{
memset(flag,0,sizeof(flag));
if(find(i)) ans++;
}
printf("%d\n",n-ans/2);
}
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  include 匈牙利