题意:很明显了。
思路:暴力搜索+剪支 。
每新加进来一个人,都与已经开设的教室里面的人进行对比,如果找到一个教室满足,教室里面所有的人都不和新加入的人认识,那么就考虑将这个人加进来。再回溯。
最后,当所有教室都不满足的时候,新增教室。
反思:dfs回溯有待提高
代码:
#include <bits/stdc++.h>
using namespace std;
const int maxn=1e6+7;
int mp[110][110];
int room[110][110];//不同房间的人数安排表
int cnt[110];//记录每个房间人数
int n,m;
int ans;
void dfs(int x,int num)
{
if(num>=ans) return;
if(x==n+1)
{
ans=min(ans,num);
return;
}
int j;
for(j=0;j<num;j++)
{
int len=cnt[j];
int cntt=0;
for(int k=0;k<len;k++)
{
if(mp[x][room[j][k]]==0)
{
cntt++;
}
}
if(cntt==len)
{
room[j][len]=x;
cnt[j]++;
dfs(x+1,num);
cnt[j]--;
room[j][len]=0;
}
}
room[num][0]=x;
cnt[num]++;
dfs(x+1,num+1);
room[num][0]=0;
cnt[num]--;
}
int main()
{
#ifndef ONLINE_JUDGE
freopen("in.txt","r",stdin);
freopen("out.txt","w",stdout);
#endif
scanf("%d%d",&n,&m);
int u,v;
memset(mp,0,sizeof(mp));
memset(room,0,sizeof(room));
memset(cnt,0,sizeof(cnt));
while(m--)
{
scanf("%d%d",&u,&v);
mp[u][v]=mp[v][u]=1;
}
ans=n;
dfs(1,0);
cout<<ans<<endl;
return 0;
}