给你一个n*n的矩阵,每一行有一个颜色,颜色是1-50,每个人有k次机会,每次可以选择一排消除这一排所有的颜色,问最后有几种颜色没有被完全消掉,没有则输出-1.
#include <iostream>
#include <cstdio>
#include <cstring>
#include <cstdlib>
#include <queue>
#include <cmath>
#include <algorithm>
using namespace std;
int map[111][111];
int n,k,s;
int link[111];
int visit[111];
bool dfs(int k)//寻找从k出发的可增广路
{
int i,j;
for(int i=1;i<=n;i++)
{
if(map[k][i]==s&&!visit[i])
{
visit[i]=1;//加入增广路
j=link[i];
if(j==-1||dfs(j))//j是未盖点 或者 从j的对应项出发有可增广路)
{
link[i]=k;
return true;//k有可增广路,返回true;
}
}
}
return false;//则从k没有可增广路,返回false;
}
int hungary()
{
int num=0;
memset(link,-1,sizeof(link));//初始化
for(int i=1;i<=n;i++)
{
memset(visit,0,sizeof(visit));
if(dfs(i))//有增广路
{
num++;//匹配数++
}
}
return num;
}
int main()
{
int a[55],color[55];
int cnt;
while(scanf("%d%d",&n,&k)!=EOF)
{
if(n==0&&k==0)
{
break;
}
cnt=0;
memset(map,0,sizeof(map));
memset(color,0,sizeof(color));
for(int i=1;i<=n;i++)
{
for(int j=1;j<=n;j++)
{
scanf("%d",&map[i][j]);
color[map[i][j]]++;
}
}
for(int i=1;i<=50;i++)
{
s=i;
if(hungary()>k&&color[i]>0)
{
a[cnt++]=i;
}
}
if(cnt==0)
{
cout<<"-1"<<endl;
}
else
{
for(int i=0;i<cnt-1;i++)
{
printf("%d ",a[i]);
}
printf("%d\n",a[cnt-1]);
}
}
return 0;
}