[hdu 5737 Necklace](http://acm.hdu.edu.cn/showproblem.php?pid=5727)
1.利用next_permulation 函数 枚举全排列下阴珠的排列;
2.利用插空法,建二分图,<阳珠——空>,被污染则<阳珠——空>为false;
3.匈牙利算法求得最大匹配数ans;
4.n-ans即为至少要被污染的阳珠数;
TLE优化:
1.全排时只要排n-1个
2.if(ans == n);即得到最大匹配了,可以直接break;
#include <bits/stdc++.h>
using namespace std;
const int maxn = 1e5+10;
const int INF = 0x3f3f3f3f;
bool mp[12][12];
int p[12];
vector <int> g[12];
bool vis[12];
int line[12];
void build(int n)
{
for(int i = 0; i < n; i++)
for(int j = 0; j < n; j++)
if(mp[i][p[j%n]] || mp[i][p[(j+1)%n]]);
else g[i].push_back(j%n);
}
bool dfs(int u)
{
for(int i = 0; i < g[u].size(); i++)
{
int v = g[u][i];
if(!vis[v])
{
vis[v] = true;
if(line[v] == -1 || dfs(line[v]))
{
line[v] = u;
return true;
}
}
}
return false;
}
int Max_match(int n)
{
memset(line,-1,sizeof(line));
int all = 0;
for(int i = 0; i < n; i++)
{
memset(vis,false,sizeof(vis));
if(dfs(i)) all++;
}
return all;
}
int main()
{
int n,m;
while(~scanf("%d%d",&n,&m))
{
memset(mp,false,sizeof(mp));
for(int i = 0; i < m; i++)
{
int j,k;
scanf("%d%d",&j,&k);
mp[j-1][k-1] = true;//berwuran
}
int ans = 0;
for(int i = 0; i <= n; i++) p[i] = i;
do{
for(int i = 0; i < n; i++)
g[i].clear();
build(n);
ans = max(ans,Max_match(n));
if(ans == n) break;
} while(next_permutation(p+1,p+n));
printf("%d\n",n-ans);
}
}